Baru -baru ini, saya menemukan persyaratan baru dalam proyek, yaitu untuk mengimplementasikan fungsi yang secara dinamis dapat menambah tugas waktu. Berbicara tentang ini, beberapa orang mungkin mengatakan itu sederhana, hanya menggunakan kuarsa, itu sederhana dan kasar. Namun, kerangka kerja kuarsa terlalu berat, dan proyek -proyek kecil tidak mudah dioperasikan. Tentu saja, beberapa orang mungkin mengatakan bahwa JDK menyediakan antarmuka pengatur waktu, yang sepenuhnya cukup. Namun, persyaratan proyek kami adalah model multi-threaded sepenuhnya, sedangkan timer adalah satu utas, jadi, dan penulis akhirnya memilih kumpulan utas JDK.
Apa itu kumpulan benang
Java menyediakan empat jenis kumpulan benang melalui pelaksana, yaitu:
newcachedthreadpool: Buat kumpulan benang yang bisa di -cache. Jika panjang pool utas melebihi kebutuhan pemrosesan, Anda dapat mendaur ulang benang idle secara fleksibel. Jika tidak ada daur ulang, buat utas baru.
NewFixEdThreadPool: Membuat kumpulan benang panjang tetap yang dapat mengontrol jumlah maksimum concurrency utas, dan kelebihan utas akan menunggu dalam antrian.
NewsCheduledThreadPool: Membuat kumpulan benang panjang tetap yang mendukung eksekusi tugas waktu dan berkala.
NewsingLetHreadExecutor: Membuat kumpulan utas berhadapan tunggal, yang hanya akan menggunakan utas pekerja yang unik untuk melaksanakan tugas, memastikan bahwa semua tugas dieksekusi dalam urutan yang ditentukan (FIFO, LIFO, Prioritas).
Poster itu menggunakan newscheduledthreadpool dalam proyek. Itu saja. Tidak peduli berapa banyak poster Anda, Anda akan memamerkan keterampilan Anda. Google dan banyak.
Mendapatkan Layanan Pool Thread
Penulis menggunakan mode singleton untuk mendapatkan layanan kumpulan utas. Kodenya adalah sebagai berikut:
/*** Penciptaan kumpulan utas. ? private threadpoolutils () {// secara manual membuat kumpulan utas. ExecutorService = baru dijadwalkanThreadPoolExecutor (10, basicThreadFactory.builder baru (). NamingPattern ("Syncdata-jadul-pool-%d"). Daemon (true) .build ()); } private static class pluginconfigholder {private final statis threadpoolutils instance = new threadPoolutils (); } public static ThreadPoolutils getInstance () {return pluginconfigholder.instance; } public jadwalExecutorService getThreadPool () {return executorService; }}Mengganggu implementasi kode utas yang berjalan
Saya tidak akan mengatakan banyak omong kosong, kodenya adalah sebagai berikut:
/*** Tugas di kumpulan utas terganggu. */Interrupthread kelas publik mengimplementasikan runnable {private int num; interupthread publik (int num) {this.num = num; } public static void main (string [] args) melempar interruptedException {thread interruptthread = utas baru (interruptThread baru (1)); TerjadwalFuture <?> T = threadpoolutils.getInstance (). GetThreadpool (). SCLETULULEATFIXEDRATE (Interrupthread, 0,2, TimeUnit.Seconds); Interupthread interrupthread1 = interrupthread baru (2); Threadpoolutils.getInstance (). GetThreadpool (). SCLETLEATFIXEDRATE (interruptthread1,0,2, timeunit.seconds); Interupthread interrupthread2 = interrupthread baru (3); Threadpoolutils.getInstance (). GetThreadPool (). SCLETLEATFIXEDRATE (interruptthread2,0,2, timeunit.seconds); Thread.sleep (5000); // hentikan interupthread thread running t.cancel (true); while (true) {}} @Override public void run () {System.out.println ("Ini adalah utas" + num); }}Catatan yang terperangkap
Ketika poster menggunakan kode berikut, dia tiba -tiba berpikir tentang bagaimana menghentikan utas dari berjalan ketika tugas waktu ini perlu dihentikan.
Threadpoolutils.getInstance (). GetThreadpool (). SCLETEAtFixEdrate (interruptthread, 0,2, timeunit.seconds);
Karena saya memiliki kebutuhan seperti itu, mari kita google itu. Setelah mencari sebagian besar waktu, saya tidak dapat menemukan informasi yang relevan. Mereka semua adalah analisis mendalam tentang java thread pool. Atau variabel global atau sesuatu, tidak ada solusi yang ditemukan untuk memuaskan penulis.
Karena tidak ada utas, mari kita lihat kode sumber yang mendasarinya dari JadwalFixedRate untuk melihat apa itu. Seperti yang diharapkan, saya melihat implementasi spesifik dari metode penjadwalanFixedRate dalam kode sumber dan menemukan bahwa nilai pengembaliannya dijadwalkan.
Publik TerjadwalFuture <?> JadwalFixedRate (perintah runnable, inisial panjang, periode panjang, unit timeunit) {if (command == null || unit == null) Lempar nullPointerException baru (); if (periode <= 0) melempar IllegalArgumentException baru (); TerjadwalFutureTask <Void> sft = new jadwalfuturetask <void> (command, null, triggertime (initialdelay, unit), unit.tonanos (periode)); RunnablesCheduledFuture <void> t = dekorateTask (perintah, sft); sft.outerTask = t; DelayedExecute (T); mengembalikan t; }Lalu mari kita lihat apa yang ada di dalam jadwal. Itu tidak mengecewakan posternya, dan saya melihat ini
BOOLEAN PUBLIK BATAS (BOOLEAN MayInterruptunning) {Boolean dibatalkan = super.cancel (MayInterruptifrunning); if (dibatalkan && removeCancel && heapIndex> = 0) hapus (ini); return dibatalkan;} // Hapus utas saat ini dari antrian public boolean yang sedang berjalan lepas (tugas runnable) {boolean dihapus = workqueue.remove (tugas); TREDTerminate (); // Dalam kasus shutdown dan sekarang kosongkan pengembalian yang dihapus;}Mari kita periksa apa itu super.cancel (mayinterruppifrunning). Kami melihat ini.
// Hentikan utas yang berjalan dengan memanggil metode interupsi dari benang public boolean cancel (boolean mayintruppifrunning) {if (! (State == baru && unsafe.comppeeAndswapint (ini, stateoffset, baru, mayintruppifrunning? Interrupting: dibatalkan))) mengembalikan palsu; coba {// jika panggilan untuk interupsi melemparkan pengecualian jika (mungkin intruptifrunning) {coba {thread t = runner; if (t! = null) t.interrupt (); } akhirnya {// state final unsafe.putorderedInt (this, stateOffset, interrupted); }}} akhirnya {finishCompletion (); } return true; }Semua masalah di sini terpecahkan.
Mari kita ringkas
Selalu ada solusi sulit dalam proyek. Ketika Google tidak mudah ditemukan, itu mungkin cara yang baik untuk mencari kode sumber JDK.