Rumah >Java >javaTutorial >Analisis kod sumber LongAdder bagi pengaturcaraan serentak Java

Analisis kod sumber LongAdder bagi pengaturcaraan serentak Java

PHPz
PHPzke hadapan
2023-05-28 08:22:171389semak imbas

Kata Pengantar

Mari kita analisa proses pelaksanaan asasnya berdasarkan kod sumber.

Kelas ini biasanya lebih disukai daripada AtomicLong apabila berbilang urutan mengemas kini jumlah biasa yang digunakan untuk tujuan seperti mengumpul statistik, bukan untuk kawalan penyegerakan yang terperinci Di bawah perbalahan kemas kini yang rendah, kedua-dua kelas mempunyai ciri yang serupa. Tetapi di bawah pertikaian yang tinggi, jangkaan daya pengeluaran kelas ini adalah lebih tinggi dengan ketara, dengan mengorbankan penggunaan ruang yang lebih tinggi.

Perenggan di atas adalah sebahagian daripada LongAdder ulasan kod sumber, diterjemahkan The maksudnya kira-kira

Kelas ini biasanya lebih baik daripada AtomicLong apabila berbilang urutan mengemas kini jumlah biasa yang digunakan untuk mengumpul statistik tetapi bukan untuk tujuan kawalan penyegerakan yang terperinci. Di bawah perbalahan kemas kini rendah, kedua-dua kelas ini mempunyai ciri yang serupa. Tetapi di bawah keadaan perbalahan yang tinggi, daya pengeluaran yang dijangkakan bagi kelas ini jauh lebih tinggi, tetapi pada kos penggunaan ruang yang lebih tinggi.

Dalam erti kata lain, LongAdder lebih cekap apabila konkurensi tinggi, tetapi kosnya adalah ruang untuk masa.

Mari kita terangkan prinsip LongAdder dengan cara yang mudah: apabila konkurensi adalah rendah, sudah cukup untuk melakukan operasi pengumpulan pada hanya satu pembolehubah base, jadi ia serupa dengan AtomicLong; tetapi apabila konkurensi meningkat , jika anda masih beroperasi pada pembolehubah base, banyak utas akan disekat, jadi buat tatasusunan cells, dan kumpulkan setiap elemen tatasusunan, dan kemudian hitung hasil akhir base dan cells hanyalah jumlah setiap elemen tatasusunan. Bit khusus dalam tatasusunan tempat benang beroperasi boleh ditentukan dengan mengira hash untuk menentukan kedudukan indeks.

Pengenalan kod sumber

LongAdderAtribut yang diwarisi daripada kelas induk Striped64 Cell di sini ialah kelas dalaman yang digunakan untuk operasi pengumpulan. Terdapat value Harta dalaman untuk menyimpan nilai terkumpul.

// CPU核心数
static final int NCPU = Runtime.getRuntime().availableProcessors();
// 并发高时进行累加的Cell数组
transient volatile Cell[] cells;
// 多个线程没有竞争时在base上进行累加
transient volatile long base;
// Cell数组是否正在创建或扩容
transient volatile int cellsBusy;

Kaedah operasi pengumpulan increment() sebenarnya memanggil add(1L), jadi mari kita lihat terus pada kaedah add

public void add(long x) {
    Cell[] as; long b, v; int m; Cell a;
    if ((as = cells) != null || !casBase(b = base, b + x)) {
        boolean uncontended = true; // 表示没有竞争
        if (as == null || (m = as.length - 1) < 0 ||
            (a = as[getProbe() & m]) == null ||
            !(uncontended = a.cas(v = a.value, v + x)))
            longAccumulate(x, null, uncontended);
    }
}

Mula-mula, mari lihat penyataan if pertama, pernyataan awal situasi cells seterusnya ialah null, jadi operasi casBase akan dilakukan, iaitu pembolehubah base akan terkumpul Jika operasi berjaya, bermakna tiada persaingan pada masa ini, jadi ia sudah berakhir.

Apabila konkurensi meningkat, kaedah casBase mungkin gagal, jadi pada masa ini, penghakiman pernyataan if kedua dimasukkan.

  • Apabila ia masuk buat kali pertama, Celltatasusunanas ialah null, jadi longAccumulate akan dilaksanakan dan Celltatasusunanas akan dimulakan dan diindeks 1 Pengumpulan kedudukan 1;

  • dan kemudian melaksanakan pernyataan if ini bukan lagi as, dan panjang tatasusunan ialah juga lebih besar daripada null0

  • , pemahaman mudah ayat ini ialah mencari kedudukan indeks secara rawak dalam tatasusunan a = as[getProbe() & m]) == null, dan menentukan sama ada nilai kedudukan itu ialah as, jika ia null Hanya laksanakan null bukannya longAccumulate dan teruskan menilai null

  • Ayat ini bermaksud operasi pengumpulan dilakukan pada kedudukan indeks yang ditemui Jika berjaya, Tamatkan operasi, jika gagal, laksanakan !(uncontended = a.cas(v = a.value, v + x))longAccumulate

Atas ialah kandungan terperinci Analisis kod sumber LongAdder bagi pengaturcaraan serentak Java. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!

Kenyataan:
Artikel ini dikembalikan pada:yisu.com. Jika ada pelanggaran, sila hubungi admin@php.cn Padam