Salinan kode adalah sebagai berikut:
paket com.yao;
impor java.util.concurrent.executorservice;
impor java.util.concurrent.Executors;
impor java.util.concurrent.future;
impor java.util.concurrent.locks.lock;
impor java.util.concurrent.locks.readwritelock;
impor java.util.concurrent.locks.reentrantlock;
impor java.util.concurrent.locks.reentrantreadwritelock;
/**
* Loker
* Konsep penting dalam pemrograman multi-threaded sedang mengunci.
* Saat melakukan operasi transaksional, sumber daya bersama perlu dikunci, yang memastikan bahwa hanya satu utas yang dapat beroperasi pada sumber daya saat melakukan operasi transaksional.
* Ini memastikan integritas data. Sebelum 5.0, fungsi penguncian diimplementasikan oleh kata kunci yang disinkronkan.
*/
Loker kelas publik {
/**
* Uji penggunaan kunci. Menggunakan kunci dalam metode ini dapat menghindari menggunakan kata kunci yang disinkronkan.
*/
Kelas Statis Publik Locktest {
Lock lock = baru reentrantlock (); // lock
nilai ganda = 0d; // nilai
int addtimes = 0;
/**
* Tingkatkan nilai nilai.
* Jadi metode ini harus disinkronkan, praktik sebelumnya adalah menggunakan kata kunci yang disinkronkan dalam deklarasi metode.
*/
public void addValue (double v) {
lock.lock (); // dapatkan kunci
System.out.println ("Locktest ke AddValue:" + V + ""
+ System.currentTimemillis ());
mencoba {
Thread.sleep (1000);
} catch (InterruptedException e) {
}
this.value += v;
this.addTimes ++;
lock.unlock (); // Lepaskan kunci
}
getValue ganda publik () {
kembalikan nilai ini;
}
}
public static void testLockTest () melempar Exception {
locktest terakhir locktest = new locktest ();
// Buat tugas baru 1 dan hubungi metode addValue dari Locktest
Runnable Task1 = new runnable () {
public void run () {
locktest.addvalue (55.55);
}
};
// Buat Tugas Baru 2 dan hubungi Metode GetValue Locktest
Runnable Task2 = new runnable () {
public void run () {
System.out.println ("Nilai:" + lockTest.getValue ());
}
};
// Buat Layanan Eksekusi Tugas Baru
ExecutorService CachedService = Executors.NewCachedThreadPool ();
Masa Depan Masa Depan = NULL;
// Jalankan tugas 1 tiga kali pada saat yang sama.
untuk (int i = 0; i <3; i ++) {
Future = CachedService.Submit (Task1);
}
// tunggu tugas terakhir 1 dieksekusi
Future.get ();
// Jalankan tugas 2 lagi untuk menghasilkan hasilnya
Future = CachedService.submit (Task2);
// Setelah menunggu Tugas 2 dieksekusi, tutup Layanan Eksekusi Tugas
Future.get ();
CachedService.shutdownnow ();
}
/**
* ReadWritelock memiliki dua kunci bawaan, satu adalah kunci baca dan yang lainnya adalah kunci tertulis.
* Beberapa utas bisa mendapatkan kunci baca secara bersamaan, tetapi hanya satu utas yang bisa mendapatkan kunci tertulis.
* Dan setelah kunci tertulis terkunci, tidak ada utas yang bisa mendapatkan kunci. Metode yang disediakan oleh ReadWritelock adalah:
* readlock (): Mengembalikan kunci baca
* writelock (): Mengembalikan kunci tertulis, kunci ini eksklusif.
* ReadWritelockTest sangat cocok untuk menangani operasi baca dan tulis dari file serupa.
* Anda dapat membaca secara bersamaan saat membaca, tetapi Anda tidak dapat menulis;
*/
kelas public static readWritelockTest {
// Kunci
ReadWritelock lock = baru reentrantreadwritelock ();
// Nilai
nilai ganda = 0d;
int addtimes = 0;
/**
* Tingkatkan nilai nilai, dan jangan mengizinkan beberapa utas untuk memasukkan metode pada saat yang sama.
*/
public void addValue (double v) {
// Dapatkan Writelock dan Lock
Lock writelock = lock.writelock ();
writelock.lock ();
System.out.println ("ReadWritelockTest ke AddValue:" + V + ""
+ System.currentTimemillis ());
mencoba {
Thread.sleep (1000);
} catch (InterruptedException e) {
}
mencoba {
// Lakukan pekerjaan menulisnya
this.value += v;
this.addTimes ++;
} Akhirnya {
// Lepaskan kunci writelock
writelock.unlock ();
}
}
/**
* Dapatkan informasi. Ketika utas memanggil metode AddValue, informasi yang diperoleh oleh GetInfo mungkin salah.
* Oleh karena itu, juga perlu untuk memastikan bahwa ketika metode dipanggil, tidak ada metode yang memanggil metode addValue.
*/
string publik getInfo () {
// Dapatkan readlock dan kunci
Kunci readlock = lock.readlock ();
readlock.lock ();
System.out.println ("ReadWritelockTest ke GetInfo"
+ System.currentTimemillis ());
mencoba {
Thread.sleep (1000);
} catch (InterruptedException e) {
}
mencoba {
// Lakukan pekerjaan membaca
return this.value + ":" + this.addtimes;
} Akhirnya {
// Rilis Readlock
readlock.unlock ();
}
}
}
public static void testreadwritelocktest () melempar Exception {
final readwritelocktest readwritelocktest = baru readwritelocktest ();
// Buat tugas baru 1 dan hubungi metode addValue dari Locktest
Runnable Task_1 = runnable baru () {
public void run () {
readwritelocktest.addvalue (55.55);
}
};
// Buat Tugas Baru 2 dan hubungi Metode GetValue Locktest
Runnable Task_2 = new runnable () {
public void run () {
System.out.println ("Info:" + ReadWritelockTest.GetInfo ());
}
};
// Buat Layanan Eksekusi Tugas Baru
ExecutorService CachedService_1 = Executors.newcachedThreadPool ();
Future Future_1 = null;
// Jalankan 5 tugas pada saat yang sama, di mana 2 tugas pertama adalah Task_1 dan dua tugas terakhir adalah Task_2
untuk (int i = 0; i <2; i ++) {
Future_1 = CachedService_1.submit (Tugas_1);
}
untuk (int i = 0; i <2; i ++) {
Future_1 = CachedService_1.submit (Tugas_2);
}
// Tugas terakhir adalah Tugas_1
Future_1 = CachedService_1.submit (Tugas_1);
// Urutan eksekusi dari 5 tugas ini harus:
// Tugas pertama dieksekusi terlebih dahulu, dan tugas kedua dieksekusi lagi;
// Lalu dua tugas_2 dieksekusi pada saat yang sama;
// Karena mereka dapat dibaca pada saat yang sama, mereka dieksekusi pada saat yang sama
// Task_1 terakhir dieksekusi lagi. Ini karena Anda tidak dapat menulis saat membaca, jadi Anda harus menunggu sampai bacaan selesai sebelum Anda bisa menulis.
// tunggu tugas terakhir yang dieksekusi
Future_1.get ();
CachedService_1.shutdownnow ();
}
public static void main (string [] args) melempar pengecualian {
Lockers.testlocktest ();
System.out.println ("---------------------");
Lockers.testreadwritelocktest ();
}
}