欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Java中對AtomicInteger和int值在多線程下遞增操作的測試

 更新時間:2014年09月19日 09:56:12   投稿:junjie  
這篇文章主要介紹了Java中對AtomicInteger和int值在多線程下遞增操作的測試,本文得出AtomicInteger操作 與 int操作的效率大致相差在50-80倍上下的結論,需要的朋友可以參考下

Java針對多線程下的數(shù)值安全計數(shù)器設計了一些類,這些類叫做原子類,其中一部分如下:

java.util.concurrent.atomic.AtomicBoolean;
java.util.concurrent.atomic.AtomicInteger;
java.util.concurrent.atomic.AtomicLong;
java.util.concurrent.atomic.AtomicReference;

下面是一個對比  AtomicInteger 與 普通 int 值在多線程下的遞增測試,使用的是 junit4;

完整代碼:

package test.java;

import java.util.concurrent.CountDownLatch;
import java.util.concurrent.atomic.AtomicInteger;

import org.junit.Assert;
import org.junit.Before;
import org.junit.Test;

/**
 * 測試AtomicInteger與普通int值在多線程下的遞增操作
 */
public class TestAtomic {

 // 原子Integer遞增對象
 public static AtomicInteger counter_integer;// = new AtomicInteger(0);
 // 一個int類型的變量
 public static int count_int = 0;

 @Before
 public void setUp() {
 // 所有測試開始之前執(zhí)行初始設置工作
 counter_integer = new AtomicInteger(0);
 }

 @Test
 public void testAtomic() throws InterruptedException {
 // 創(chuàng)建的線程數(shù)量
 int threadCount = 100;
 // 其他附屬線程內(nèi)部循環(huán)多少次
 int loopCount = 10000600;
 // 控制附屬線程的輔助對象;(其他await的線程先等著主線程喊開始)
 CountDownLatch latch_1 = new CountDownLatch(1);
 // 控制主線程的輔助對象;(主線程等著所有附屬線程都運行完畢再繼續(xù))
 CountDownLatch latch_n = new CountDownLatch(threadCount);
 // 創(chuàng)建并啟動其他附屬線程
 for (int i = 0; i < threadCount; i++) {
  Thread thread = new AtomicIntegerThread(latch_1, latch_n, loopCount);
  thread.start();
 }
 long startNano = System.nanoTime();
 // 讓其他等待的線程統(tǒng)一開始
 latch_1.countDown();
 // 等待其他線程執(zhí)行完
 latch_n.await();
 //

 long endNano = System.nanoTime();
 int sum = counter_integer.get();
 //
 Assert.assertEquals("sum 不等于 threadCount * loopCount,測試失敗",
  sum, threadCount * loopCount);
 System.out.println("--------testAtomic(); 預期兩者相等------------");
 System.out.println("耗時: " + ((endNano - startNano) / (1000 * 1000)) + "ms");
 System.out.println("threadCount = " + (threadCount) + ";");
 System.out.println("loopCount = " + (loopCount) + ";");
 System.out.println("sum = " + (sum) + ";");
 }

 @Test
 public void testIntAdd() throws InterruptedException {
 // 創(chuàng)建的線程數(shù)量
 int threadCount = 100;
 // 其他附屬線程內(nèi)部循環(huán)多少次
 int loopCount = 10000600;
 // 控制附屬線程的輔助對象;(其他await的線程先等著主線程喊開始)
 CountDownLatch latch_1 = new CountDownLatch(1);
 // 控制主線程的輔助對象;(主線程等著所有附屬線程都運行完畢再繼續(xù))
 CountDownLatch latch_n = new CountDownLatch(threadCount);
 // 創(chuàng)建并啟動其他附屬線程
 for (int i = 0; i < threadCount; i++) {
  Thread thread = new IntegerThread(latch_1, latch_n, loopCount);
  thread.start();
 }
 long startNano = System.nanoTime();
 // 讓其他等待的線程統(tǒng)一開始
 latch_1.countDown();
 // 等待其他線程執(zhí)行完
 latch_n.await();
 //
 long endNano = System.nanoTime();
 int sum = count_int;
 //
 Assert.assertNotEquals(
  "sum 等于 threadCount * loopCount,testIntAdd()測試失敗", 
  sum, threadCount * loopCount);
 System.out.println("-------testIntAdd(); 預期兩者不相等---------");
 System.out.println("耗時: " + ((endNano - startNano) / (1000*1000))+ "ms");
 System.out.println("threadCount = " + (threadCount) + ";");
 System.out.println("loopCount = " + (loopCount) + ";");
 System.out.println("sum = " + (sum) + ";");
 }

 // 線程
 class AtomicIntegerThread extends Thread {
 private CountDownLatch latch = null;
 private CountDownLatch latchdown = null;
 private int loopCount;

 public AtomicIntegerThread(CountDownLatch latch,
  CountDownLatch latchdown, int loopCount) {
  this.latch = latch;
  this.latchdown = latchdown;
  this.loopCount = loopCount;
 }

 @Override
 public void run() {
  // 等待信號同步
  try {
  this.latch.await();
  } catch (InterruptedException e) {
  e.printStackTrace();
  }
  //
  for (int i = 0; i < loopCount; i++) {
  counter_integer.getAndIncrement();
  }
  // 通知遞減1次
  latchdown.countDown();
 }
 }

 // 線程
 class IntegerThread extends Thread {
 private CountDownLatch latch = null;
 private CountDownLatch latchdown = null;
 private int loopCount;

 public IntegerThread(CountDownLatch latch, 
  CountDownLatch latchdown, int loopCount) {
  this.latch = latch;
  this.latchdown = latchdown;
  this.loopCount = loopCount;
 }

 @Override
 public void run() {
  // 等待信號同步
  try {
  this.latch.await();
  } catch (InterruptedException e) {
  e.printStackTrace();
  }
  //
  for (int i = 0; i < loopCount; i++) {
  count_int++;
  }
  // 通知遞減1次
  latchdown.countDown();
 }
 }
}

普通PC機上的執(zhí)行結果類似如下:

--------------testAtomic(); 預期兩者相等-------------------
耗時: 85366ms
threadCount = 100;
loopCount = 10000600;
sum = 1000060000;
--------------testIntAdd(); 預期兩者不相等-------------------
耗時: 1406ms
threadCount = 100;
loopCount = 10000600;
sum = 119428988;

從中可以看出, AtomicInteger操作 與 int操作的效率大致相差在50-80倍上下,當然,int很不消耗時間,這個對比只是提供一個參照。

如果確定是單線程執(zhí)行,那應該使用 int; 而int在多線程下的操作執(zhí)行的效率還是蠻高的, 10億次只花了1.5秒鐘;

 (假設CPU是 2GHZ,雙核4線程,理論最大8GHZ,則每秒理論上有80億個時鐘周期,

 10億次Java的int增加消耗了1.5秒,即 120億次運算, 算下來每次循環(huán)消耗CPU周期 12個;

個人覺得效率不錯, C 語言也應該需要4個以上的時鐘周期(判斷,執(zhí)行內(nèi)部代碼,自增判斷,跳轉(zhuǎn))

 前提是: JVM和CPU沒有進行激進優(yōu)化.

)

而 AtomicInteger 效率其實也不低,10億次消耗了80秒, 那100萬次大約也就是千分之一,80毫秒的樣子.

相關文章

  • Spring實戰(zhàn)之XML與JavaConfig的混合配置詳解

    Spring實戰(zhàn)之XML與JavaConfig的混合配置詳解

    大家都知道Spring的顯示配置方式有兩種,一種是基于XML配置,一種是基于JavaConfig的方式配置。那么下這篇文章主要給大家分別介紹如何在JavaConfig中引用XML配置的bean以及如何在XML配置中引用JavaConfig,需要的朋友可以參考下。
    2017-07-07
  • Java多線程之哲學家就餐問題詳解

    Java多線程之哲學家就餐問題詳解

    這篇文章主要介紹了Java多線程之哲學家就餐問題詳解,文中有非常詳細的代碼示例,對正在學習java的小伙伴們有非常好的幫助,需要的朋友可以參考下
    2021-04-04
  • 詳解Java打包及上傳到私服務的方法

    詳解Java打包及上傳到私服務的方法

    這篇文章主要介紹了Java打包及上傳到私服務的方法,本文給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友參考下吧
    2024-01-01
  • java實現(xiàn)帶有背景圖片的窗體

    java實現(xiàn)帶有背景圖片的窗體

    這篇文章主要為大家詳細介紹了java實現(xiàn)帶有背景圖片的窗體,文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2021-03-03
  • SpringBoot2.6.x升級后循環(huán)依賴及Swagger無法使用問題

    SpringBoot2.6.x升級后循環(huán)依賴及Swagger無法使用問題

    這篇文章主要為大家介紹了SpringBoot2.6.x升級后循環(huán)依賴及Swagger無法使用問題,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2022-06-06
  • SpringMVC中RequestMapping注解(作用、出現(xiàn)的位置、屬性)

    SpringMVC中RequestMapping注解(作用、出現(xiàn)的位置、屬性)

    這篇文章主要介紹了SpringMVC中RequestMapping注解(作用、出現(xiàn)的位置、屬性),本文給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2021-01-01
  • Java設計模式之適配器模式詳解

    Java設計模式之適配器模式詳解

    這篇文章主要介紹了Java設計模式之適配器模式詳解,適配器模式將一個類的接口轉(zhuǎn)換成客戶希望的另一個接口,Adapter模式使得原本由于接口不兼容而不能一起工作的哪些類可以一起工作,需要的朋友可以參考下
    2023-09-09
  • NoHttpResponseException問題分析解決記錄

    NoHttpResponseException問題分析解決記錄

    這篇文章主要為大家介紹了NoHttpResponseException問題分析解決記錄,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2023-08-08
  • 如何理解Java線程池及其使用方法

    如何理解Java線程池及其使用方法

    線程池是首先創(chuàng)建一些線程,它們的集合稱為線程池。使用線程池可以提高性能,它在系統(tǒng)啟動時創(chuàng)建大量空閑的線程,程序?qū)⒁粋€任務傳給線程池,它就會啟動一條線程來執(zhí)行這個任務,執(zhí)行結束以后,該線程并不會死亡,而是再次返回線程池中成為空閑狀態(tài),等待執(zhí)行下一個任務
    2021-06-06
  • Springboot Vue可配置調(diào)度任務實現(xiàn)示例詳解

    Springboot Vue可配置調(diào)度任務實現(xiàn)示例詳解

    這篇文章主要為大家介紹了Springboot Vue可配置調(diào)度任務實現(xiàn)示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2023-01-01

最新評論