Kolam utas dapat menjalankan beberapa tugas secara bersamaan. Terkadang, kami mungkin ingin melacak hasil eksekusi tugas. Bahkan dalam periode waktu tertentu, jika tugas tidak selesai, kami mungkin juga ingin membatalkan eksekusi tugas. Untuk mendukung fitur ini, ThreadPoolExecutor menyediakan Futuretask untuk melacak eksekusi dan pembatalan tugas. Artikel ini memperkenalkan prinsip implementasi Futuretask.
Untuk lebih memahami prinsip implementasi Futuretask, pertama -tama kami menyediakan beberapa antarmuka dan struktur kelas yang penting, seperti yang ditunjukkan pada gambar di bawah ini:
ThreadPoolExecutor menyediakan antarmuka pengiriman untuk mengirimkan tugas. Kirim mendukung dua antarmuka yang berbeda: runnable dan callable. Untuk menyediakan antarmuka eksternal terpadu, JDK secara internal membungkus yang dapat diubah, yang semuanya diimplementasikan melalui adaptor RunNableAdapter. Berikut ini adalah kode sumber RunNableAdapter:
Static Final Class RunNableAdapter <T> mengimplementasikan Callable <T> {Final Runnable Task; hasil t terakhir; RunNableAdapter (Runnable Task, t hasil) {this.task = tugas; this.result = hasil; } public t call () {task.run (); hasil pengembalian; }}RunNableAdapter adalah kelas implementasi Callable, yang mengimplementasikan metode panggilan. Metode panggilan hanya memanggil tugas.run () dan kemudian mengembalikan hasilnya, yang memastikan bahwa hanya antarmuka yang dapat dipanggil yang perlu ditangani secara seragam secara internal.
Melalui bagian sebelumnya, kita tahu bahwa tugas runnable yang dikirimkan secara internal dikonversi ke tugas yang dapat dipanggil. Periksa nilai pengembalian metode pengiriman, yang merupakan masa depan. Faktanya, masa depan ini adalah contoh Futuretask. Melalui contoh ini, memanggil metode GET dapat memblokir utas saat ini sampai tugas selesai dan hasilnya dikembalikan.
Seluruh rantai panggilan terlihat seperti ini:
Thread Pekerja -> futuretask.run () -> callable.call () -> Task.run ()
Jika tugas yang dapat dipanggil dikirimkan, hanya ada tiga panggilan pertama.
Untuk menunjukkan seluruh proses dengan lebih baik, contoh -contoh berikut akan digunakan untuk menunjukkan proses eksekusi.
1. Kirim tugas yang dapat dipanggil ke kumpulan utas (Runnable juga akan dikonversi ke Callable). Pada saat ini, Callable diteruskan ke instance Futuretask, seperti yang ditunjukkan di bawah ini:
2. Kumpulan utas menggunakan utas untuk menjalankan tugas Futuretask.
Proses menjalankan tugas relatif sederhana. Pada akhirnya, metode callable.call () atau runnable.run () akan dipanggil, dan hasilnya akan diperoleh, yang akan menyimpan hasil dalam properti hasil dari instance futuretask, dan status akan dimodifikasi menjadi normal, menunjukkan bahwa tugas telah dieksekusi dan hasilnya dapat diperoleh.
Kami berasumsi bahwa beberapa utas memanggil metode GET dari instance Futuretask yang sama selama pelaksanaan callable.call() . Pada saat ini, utas ini akan diblokir dan disimpan dalam tumpukan, seperti yang ditunjukkan pada gambar di bawah ini:
Threads 1, 2, dan 3 hubungi metode FutureTask.get . Karena tugas belum dieksekusi, ketiga utas akan diblokir dan mengantuk. Ada tumpukan di Futuretask untuk menyimpan utas menunggu. Pointer teratas dari tumpukan dirujuk oleh FutureTask.waiters . Ketika tugas dieksekusi, utas di seluruh tumpukan akan mengulangi. Pada saat ini, setiap utas akan dibangunkan dan hasil eksekusi tugas dapat berhasil diperoleh (hasil eksekusi disimpan di FutureTask.outcome) .
Futuretask juga mendukung fungsi pembatalan tugas, yang semuanya mengoordinasikan banyak utas melalui keadaan Futuretask.
Antarmuka Futuretask adalah mekanisme implementasi yang memberi kita pelacakan dan mengendalikan pelaksanaan tugas. Dibandingkan dengan kumpulan utas itu sendiri, itu relatif sederhana dan saya percaya tidak sulit untuk dipahami.
Di atas adalah semua konten artikel ini tentang prinsip implementasi Futuretask di java thread pool. Saya harap ini akan membantu semua orang. Teman yang tertarik dapat terus merujuk ke topik terkait lainnya di situs ini. Jika ada kekurangan, silakan tinggalkan pesan untuk menunjukkannya. Terima kasih teman atas dukungan Anda untuk situs ini!