Khi một chương trình java khởi chạy JVM sẽ tạo 1 thread gọi là main thread sẽ được khởi tạo và đây là nơi thực thi chương trình. Ngoài ra chúng ta có thể tạo thêm các thread khác tùy vào nhu cầu sử dụng. Khi chương trình tạo ra các thread khác ngoài main thread thì nhu cầu về đồng bộ hóa là cần thiết để tránh dẫn đến deadlock hoặc thu được các kết quả không mong muốn. Khi sử dụng wait(), join(), sleep() method để đồng bộ hóa có ai đặt câu hỏi rằng thread lúc này đang ở trạng thái nào không? Trong bài viết này chúng ta sẽ cùng tìm hiểu vòng đời của một thread, các trạng thái mà nó trải qua trước khi chết đi.
Về cơ bản một thread có các trạng thái sau:
- New – Tạo mới
- Runnable – Đang thực thi
- Blocked – Bị chặn
- Waiting – Trạng thái chờ
- Timed Waiting – Trạng thái chờ trong một khoảng thời gian xác định
- Terminated – Chấm dứt
Vòng đời của một thread
Ở trên chúng ta đã đi sơ lược về các trạng thái tồn tại trong vòng đời của một thread. Dưới đây chúng ta sẽ tìm hiểu kỹ hơn về một trạng thái của thread như là chúng được tạo ra khi nào? khi nào chúng kết thúc? ai tác động đến trạng thái đó!
New: Khi một thread mới được tạo nó sẽ nằm ở trạng thái new. Lúc này thread sẽ chưa được khởi chạy cho đến khi start() method được gọi.
Runnable: Khi start() method thread sẽ sẵn sàng để thực thi, tuy nhiên không phải là nó sẽ chạy ngay sau khi start() được gọi mà còn phụ thuộc vào hoạt động điều phối của chương trình, hệ thống, bộ lập lịch etc.
Blocked/Waiting:
- Khi một thread ngừng hoạt động tạm thời trong một khoảng thời gian thì nó sẽ nằm 1 trong 2 trạng thái Blocked hoặc Waiting.
- Khi một thread chờ một tác vụ I/O thực thi hoàn tất, nó đang ở trong trạng thái Blocked. Khi đang ở trong trại thái này thread sẽ không thể thực thi thêm bất kỳ đoạn mã nào của nó cho đến khi nó được chuyển sang trạng thái Runnable.
- Các thread sẽ bị chặn khi cố truy cập vào một đoạn mã code đang được chiếm bởi một thread khác, lúc này chúng sẽ rơi vào trạng thái Blocked. Khi đoạn mã được thread chiếm đóng giải phóng, chương trình sẽ chọn 1 trong số các thread chờ để thực thi đoạn mã hoặc do các điều kiện mà chúng ta đưa ra thì chúng ta chuyển sang trạng thái Waiting. Khi một thread được chọn để thực thi đoạn mã thì nó sẽ chuyển sang trạng thái Runnable.
Timed Waiting: Các thread sẽ chuyển sang trạng thái Timed Waiting khi các method wait(), join() được gọi với một khoản thời gian cụ thể. Sau khi hết thời gian chờ chúng sẽ quay trở lại với trạng thái Runnable.
Terminated: Một thread sẽ kết thúc chu trình sống sau khi chúng đã thực thi hết mã bên trong nó hoặc xảy ra một lỗi ngoại lệ nào đó. Sau khi chuyển qua trạng thái Terminated thread sẽ không còn tiêu tốn tài nguyên của CPU và đợi cho đến khi trình dọn rác dọn dẹp.
Ví dụ vòng đời của thread trong java
class thread implements Runnable { public void run() { // moving thread2 to timed waiting state try { Thread.sleep(1500); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("State of thread1 while it called join() method on thread2 -" + Test.thread1.getState()); try { Thread.sleep(200); } catch (InterruptedException e) { e.printStackTrace(); } } } class Test implements Runnable { public static Thread thread1; public static Test obj; public static void main(String[] args) { obj = new Test(); thread1 = new Thread(obj); // thread1 created and is currently in the NEW state. System.out.println("State of thread1 after creating it - " + thread1.getState()); thread1.start(); // thread1 moved to Runnable state System.out.println("State of thread1 after calling .start() method on it - " + thread1.getState()); } public void run() { thread myThread = new thread(); Thread thread2 = new Thread(myThread); // thread1 created and is currently in the NEW state. System.out.println("State of thread2 after creating it - " + thread2.getState()); thread2.start(); // thread2 moved to Runnable state System.out.println("State of thread2 after calling .start() method on it - " + thread2.getState()); // moving thread1 to timed waiting state try { //moving thread1 to timed waiting state Thread.sleep(200); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("State of thread2 after calling .sleep() method on it - " + thread2.getState()); try { // waiting for thread2 to die thread2.join(); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("State of thread2 when it has finished it's execution - " + thread2.getState()); } }
Output:
State of thread1 after creating it – NEW
State of thread1 after calling .start() method on it – RUNNABLE
State of thread2 after creating it – NEW
State of thread2 after calling .start() method on it – RUNNABLE
State of thread2 after calling .sleep() method on it – TIMED_WAITING
State of thread1 while it called join() method on thread2 -WAITING
State of thread2 when it has finished it’s execution – TERMINATED
Nguồn tham khảo
https://www.geeksforgeeks.org/lifecycle-and-states-of-a-thread-in-java/