Arithmeticexception là gì

Từ khóa throw trong Java được sử dụng để ném ra một exception tường minh. Chúng ta có thể ném hoặc Checked Exception hoặc Unchecked Exception trong Java bởi từ khóa throw. Từ khóa throw được sử dụng chủ yếu để ném các Custom Exception (là các exception được định nghĩa bởi lập trình viên).

Cú pháp từ khóa throw:

Ví dụ về throw IOException.

throw new IOException("File không tồn tại");

Ví dụ về từ khóa throw trong java

throw ra ngoại lệ nhưng không xử lý: Trong ví dụ này, chúng ta tạo ra phương thức validate() với tham số truyền vào là giá trị integer. Nếu tuổi dưới 18, chúng ta ném ra ngoại lệ ArithmeticException nếu không in ra một thông báo "welcome".

public class TestThrow1 {
    static void validate(int age) {
        if (age < 18)
            throw new ArithmeticException("not valid");
        else
            System.out.println("welcome");
    }

    public static void main(String args[]) {
        validate(13);
        System.out.println("rest of the code...");
    }
}

Exception in thread "main" java.lang.ArithmeticException: not valid

throw ra ngoại lệ nhưng có xử lý

public class TestThrow2 {
    static void validate(int age) {
        try {
            if (age < 18)
                throw new ArithmeticException("not valid");
            else
                System.out.println("welcome");
        } catch (ArithmeticException ex) {
            System.out.println(ex.getMessage());
        }
    }

    public static void main(String args[]) {
        validate(13);
        System.out.println("rest of the code...");
    }
}

not valid
rest of the code...

Nội Dung

  • 1. Ngoại lệ và xử lý ngoại lệ trong Java là gì?
    • 1.1. Ngoại lệ trong Java là gì?
    • 1.2. Xử lý ngoại lệ trong Java là gì?
  • 2. Các loại ngoại lệ trong Java
  • 3. Hệ thống cấp bậc của ngoại lệ trong Java
  • 4. Lợi ích của Exception trong Java
    • 4.1. Phát hiện và xử lý lỗi hiệu quả
    • 4.2. Xử lý lỗi một cách linh hoạt trong việc gọi method lồng nhau
  • 5. Một số ngoại lệ phổ biến có thể xảy ra trong Java
    • 5.1. Chia một số cho 0
    • 5.2. Thao tác với giá trị rỗng
    • 5.3. Lỗi ép kiểu
    • 5.4. Thêm phần tử sai index trong mảng
    • 5.5. Kích thước mảng là số âm

1. Ngoại lệ và xử lý ngoại lệ trong Java là gì?

1.1. Ngoại lệ trong Java là gì?

Trong Java ngoại lệ hay còn gọi là Exception, là một sự kiện chỉ xảy ra trong chương trình Java khi thực thi thực thi một chương trình nào đó. Nó sẽ phá vỡ luồng chuẩn của chương trình. Lúc này chương trình sẽ bị gián đoạn và dừng lại bất thường. Một thông báo lỗi nào đó sẽ được ném ra. Đó chính là Exception – ngoại lệ trong Java. Ta có thể hiểu ngắn gọi lại ngoại lệ có nghĩa là một vấn đề hoặc một tình trạng bất thường khiến chương trình máy tính ngừng xử lý thông tin theo cách bình thường.

Một ngoại lệ có thể xảy ra với nhiều lý do khác nhau, ví dụ như:

  • Nhập sai dữ liệu
  • Mở file mà lại không tìm thấy file tương ứng
  • Mất mạng trong quá trình khởi chạy
  • Thiết bị gặp lỗi

Một vài những ngoại lệ xảy ra bởi lỗi của người dùng, một số khác bởi lỗi của lập trình viên và số khác nữa đến từ lỗi của nguồn dữ liệu vật lý. Khi một ngoại lệ xảy ra trong một phương thức, nó sẽ tạo ra một đối tượng. Đối tượng này được gọi là đối tượng ngoại lệ. Nó chứa thông tin về ngoại lệ như tên và mô tả của ngoại lệ và trạng thái của chương trình khi ngoại lệ xảy ra. Java Exeption được triển khai bằng cách sử dụng các lớp như Throwable, Exception, RuntimeException và các từ khóa như throw , throws , try , catchfinally.

1.2. Xử lý ngoại lệ trong Java là gì?

Xử lý ngoại lệ trong Java – Exception Handling là kỹ thuật để xử lý các lỗi khi runtime như ClassNotFound, IO, SQL, Remote, … Nó giúp duy trì luồng chuẩn của ứng dụng vì Exception thường phá vỡ luồng chuẩn của ứng dụng.

Có một số cách để xử lý ngoại lệ như:

  • Sử dụng khối try…catch để xử lý.
  • Sử dụng multicatch để bắt nhiều ngoại lệ.
  • Sử dụng khối try…catch…finally.
  • Sử dụng try with resource.
  • Sử dụng Nested try (lồng một khối try trong một try khác).
  • Sử dụng từ khóa throw và throws.

Ví dụ: ta có chương trình sau

public class Main {
    public static void main(String[] args) {
        System.out.println("Three");
        // Phép chia này không có vấn đề.
        int value = 10 / 2;
        System.out.println("Two");
        // Phép chia này không có vấn đề.
        value = 10 / 1;
        System.out.println("One");
        // Phép chia này có vấn đề, chia cho 0.
        // Lỗi đã xẩy ra tại đây.
        value = 10 / 0;
        // Và dòng code dưới đây sẽ không được thực hiện.
        System.out.println("Laptrinhtudau.com!");

    }

}

Kết quả

Three
Two
One
Exception in thread "main" java.lang.ArithmeticException: / by zero
    at Main.main(Main.java:12)

Ta thấy chương trình vừa báo lỗi mà vừa in được một số kết quả ra màn hình. Tại sao vậy? Vì chương trình chạy hoàn toàn bình thường tại các bước đầu tiên. Nhưng đến khi thực hiện phép chia cho 0 thì vấn đề đã xảy ra. Hay ngoại lệ đã được ném ra. Lúc này ta cần xử lý ngoại lệ để chương trình hoạt động lại bình thường. Các bạn có thể tham khảm ví dụ sau về việc xử lý ngoại lệ.

public class Main {
    public static void main(String[] args) {
        System.out.println("Three");
        // Phép chia này hoàn toàn không có vấn đề.
        int value = 10 / 2;
        System.out.println("Two");
        // Phép chia này cũng vậy.
        value = 10 / 1;
        System.out.println("One");
        try {
            // Phép chia này có vấn đề, chia cho 0.
            // Một lỗi đã xẩy ra tại đây.
            value = 10 / 0;
            // Dòng code này sẽ không được thực thi.
            System.out.println("Value =" + value);
        } catch (ArithmeticException e) {
            // Các dòng code trong catch được thực thi.
            System.out.println("Error: " + e.getMessage());
            // Các dòng code trong catch được thực thi.
            System.out.println("Ignore...");
        }
        // Dòng code này sẽ được thực thi.
        System.out.println("Laptrinhtudau.com");
    }
}

Kết quả

Three
Two
One
Error: / by zero
Ignore...
Laptrinhtudau.com

2. Các loại ngoại lệ trong Java

Trong Java chủ yếu có 2 loại loại Exception là Checked Exception và Unchecked Exception. Nhưng mỗi error được coi là Unchecked Exception. Tuy nhiên, ta thể hiểu thêm Error là một loại ngoại lệ và có ba loại Exception:

  • Checked Exception : là các Exception xảy ra tại thời điểm Compile time (là thời điểm chương trình đang được biên dịch). Những Exception này thường liên quan đến lỗi cú pháp (syntax) và bắt buộc chúng ta phải “bắt” (catch) nó.
  • Unchecked Exception: là các Exception xảy ra tại thời điểm Runtime (là thời điểm chương trình đang chạy). Những Exception này thường liên quan đến lỗi logic và không bắt buộc chúng ta phải “bắt” (catch) nó.
  • Error : là những lỗi nghiêm trọng xảy ra đối khi chương trình hoạt động mà lập trình viên không thể kiểm soát. Ví dụ như lỗi phần cứng, tràn bộ nhớ, hay lỗi của JVM. Thông thường các chương trình không thể khôi phục với Error

Ví dụ:

  • CheckedException
public class Main{
     public static void main(String[] args) {
    System.out.println(ABC);
    }	
}

Lúc này, ngay tại dòng code System.out.println(ABC); sẽ bị lỗi. Lý do là vì ví dụ này mục đích là để hiển thị một chuỗi, mà đã hiển thị chuỗi thì bắt buộc chuỗi đó phải nằm trong cặp dấu “” . Đây chính là Checked Exception, lúc này nếu chúng ta tiến hành chạy chương trình thì sẽ có thông báo lỗi hiển thị.

  • Unchecked Exception
public class Main {
    public static void main(String[] args) {
        int a = 5, b = 0;
        System.out.println(a/b);
    }

}

Lúc này, chương trình sẽ không báo lỗi gì trong đoạn code của chúng ta nhưng khi biên dịch thì sẽ có thông báo lỗi “/ by zero” (lỗi chia cho 0). Đây chính là Unchecked Exception.

3. Hệ thống cấp bậc của ngoại lệ trong Java

Tất cả các lớp Exception đều là lớp con của lớp java.lang.Exception . Lớp Exception là lớp con của lớp Throwable. Một loại lớp Exception khác là Error cũng là lớp con của lớp Throwable.

Như mình đã nói ở trên thì Erros không thường được đặt bẫy bởi các chương trình Java và thường được tạo ra để thể hiện lỗi trong môi trường runtime và làm chết chương trình. Lớp Error định nghĩa các ngoại lệ mà không thể bắt (catch) từ chương trình.

4.1. Phát hiện và xử lý lỗi hiệu quả

Exception giúp ta tổ chức source code trong việc phát hiện, xử lý lỗi một cách hiệu quả nhất. Exception cho phép ta viết code xử lý luồng logic chính một cách liền mạch, khiến code trở nên đơn giản, dễ đọc hơn.

Ta có thể xét ví dụ về phương thức readFile như sau:

readFile {
    open the file;
    determine its size;
    allocate that much memory;
    read the file into memory;
    close the file;
}

Trên là method đọc và xử lý file một cách đơn giản, nhưng nó đã bỏ qua các lỗi tiềm ẩn như: lỗi khi mở file, lỗi xác định kích thước file, lỗi tràn bộ nhớ, lỗi không đọc được file, lỗi không thể đóng file. Nếu bắt và xử lý lỗi theo cách “truyền thống” thì method readFile được tổ chức như sau.

errorCodeType readFile {
    initialize errorCode = 0;
    open the file;
    if (theFileIsOpen) {
        determine the length of the file;
        if (gotTheFileLength) {
            allocate that much memory;
            if (gotEnoughMemory) {
                read the file into memory;
                if (readFailed) {
                    errorCode = -1;
                }
            } else {
                errorCode = -2;
            }
        } else {
            errorCode = -3;
        }
        close the file;
        if (theFileDidntClose && errorCode == 0) {
            errorCode = -4;
        } else {
            errorCode = errorCode and -4;
        }
    } else {
        errorCode = -5;
    }
    return errorCode;
}

Rất rối và nhiều câu lệnh if else . Giả sử mà ta chỉ nhầm một dấu ngoặc thôi cũng khá mệt rồi. Và Exception sẽ giúp ta giải quyết vấn đề này

readFile {
    try {
        open the file;
        determine its size;
        allocate that much memory;
        read the file into memory;
        close the file;
    } catch (fileOpenFailed) {
       doSomething;
    } catch (sizeDeterminationFailed) {
        doSomething;
    } catch (memoryAllocationFailed) {
        doSomething;
    } catch (readFailed) {
        doSomething;
    } catch (fileCloseFailed) {
        doSomething;
    }
}

4.2. Xử lý lỗi một cách linh hoạt trong việc gọi method lồng nhau

Giả xử phương thức readFile được gọi từ chương trình chính thông qua các method như sau.

method1 {
    call method2;
}

method2 {
    call method3;
}

method3 {
    call readFile;
}

Nếu các method method2, method3 không quan tâm đến việc xử lý lỗi khi method readFile “bắn” ra mà ta muốn xử lý lỗi ở method method1 thì method2, method3 chỉ việc “forward” ngoại lệ cho các method phía trên như sau.

method1 {
    try {
        call method2;
    } catch (exception e) {
        doErrorProcessing;
    }
}

method2 throws exception {
    call method3;
}

method3 throws exception {
    call readFile;
}

5. Một số ngoại lệ phổ biến có thể xảy ra trong Java

5.1. Chia một số cho 0

Nếu chúng ta chia bất kỳ số nào cho số 0, sẽ xảy ra ngoại lệ ArithmeticException.

Ví dụ:

public class Main {
    public static void main(String[] args) {
        int a = 5, b = 0;
        System.out.println(a/b);
    }

}

Kết quả

Exception in thread "main" java.lang.ArithmeticException: / by zero
    at Main.main(Main.java:4)

5.2. Thao tác với giá trị rỗng

Nếu chúng ta có bất kỳ biến nào có giá trị null , thực hiện bất kỳ hoạt động nào bởi biến đó sẽ xảy ra ngoại lệ NullPointerException.

Ví dụ:

public class Main {
    public static void main(String[] args) {
       String s=null;  
       System.out.println(s.length());
    }

}

Kết quả

Exception in thread "main" java.lang.NullPointerException
    at Main.main(Main.java:4)

5.3. Lỗi ép kiểu

Sự định dạng sai của bất kỳ giá trị nào, có thể xảy ra ngoại lệ NumberFormatException. Giả sử ta có một biến String có giá trị là các ký tự, chuyển đổi biến này thành số sẽ xảy ra NumberFormatException

Ví dụ:

public class Main {
    public static void main(String[] args) {
                String s="abc";  
        int i=Integer.parseInt(s);
    }

}

Kết quả

Exception in thread "main" java.lang.NumberFormatException: For input string: "abc"
    at java.base/java.lang.NumberFormatException.forInputString(NumberFormatException.java:68)
    at java.base/java.lang.Integer.parseInt(Integer.java:652)
    at java.base/java.lang.Integer.parseInt(Integer.java:770)
    at Main.main(Main.java:4)

5.4. Thêm phần tử sai index trong mảng

Nếu ta chèn bất kỳ giá trị nào vào index sai, sẽ xảy ra ngoại lệ ArrayIndexOutOfBoundsException

Ví dụ:

public class Main {
    public static void main(String[] args) {
             int a[]=new int[5];  
             a[10]=50;
      }
}

Kết quả

Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: Index 10 out of bounds for length 5
    at Main.main(Main.java:4)

5.5. Kích thước mảng là số âm

Nếu ta cho kích thước mảng là số âm ngoại lệ NegativeArraySizeException được ném ra

Ví dụ:

public class Main {
    public static void main(String[] args) {
            int[] arr = new int[-5];
    }
}

Kết quả

Exception in thread "main" java.lang.NegativeArraySizeException: -5
    at Main.main(Main.java:3)

Ngoại lệ trong Java là gì?

Một exception (ngoại lệ) trong Java là một vấn đề xảy ra trong quá trình thực hiện của chương trình. Một ngoại lệ có thể xảy ra với nhiều lý do khác nhau, như dưới đây: Người dùng nhập dữ liệu không hợp lệ. Một file cần được mở nhưng không thể tìm thấy.

Ngoài lề là gì Tại sao phải xử lý ngoại lệ?

Ngoại lệ có nghĩa một vấn đề hoặc một tình trạng bất thường khiến chương trình máy tính ngừng xử lý thông tin theo cách bình thường. Ngoại lệ trong Java một đối tượng đại diện cho một lỗi hoặc một sự kiện bất ngờ xảy ra khi chương trình chạy và làm gián đoạn luồng thực thi bình thường của chương trình.

Một ngoại lệ là gì?

Một ngoại lệ trong Java xảy ra trong quá trình thực thi một chương trình. Ngoại lệ là các sự kiện không mong muốn xảy ra trong thời gian chạy và làm gián đoạn luồng thực thi chương trình bình thường.

Java làng RuntimeException là gì?

RuntimeException là lớp cơ sở của tất cả các lớp unchecked exception. Đó cũng dấu hiệu để nhận biết đâu checked exception và đâu unchecked exception. Điểm khác biệt giữa các lớp checked và unchecked expcetion chính thời điểm xác định được expcetion có thể xảy ra.