程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> JAVA編程 >> 關於JAVA >> Java中對AtomicInteger和int值在多線程下遞增操作的測試

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

編輯:關於JAVA

Java中對AtomicInteger和int值在多線程下遞增操作的測試。本站提示廣大學習愛好者:(Java中對AtomicInteger和int值在多線程下遞增操作的測試)文章只能為提供參考,不一定能成為您想要的結果。以下是Java中對AtomicInteger和int值在多線程下遞增操作的測試正文


Java針對多線程下的數值平安計數器設計了一些類,這些類叫做原子類,個中一部門以下:

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() {
 // 一切測試開端之前履行初始設置任務
 counter_integer = new AtomicInteger(0);
 }

 @Test
 public void testAtomic() throws InterruptedException {
 // 創立的線程數目
 int threadCount = 100;
 // 其他從屬線程外部輪回若干次
 int loopCount = 10000600;
 // 掌握從屬線程的幫助對象;(其他await的線程先等著主線程喊開端)
 CountDownLatch latch_1 = new CountDownLatch(1);
 // 掌握主線程的幫助對象;(主線程等著一切從屬線程都運轉終了再持續)
 CountDownLatch latch_n = new CountDownLatch(threadCount);
 // 創立並啟動其他從屬線程
 for (int i = 0; i < threadCount; i++) {
  Thread thread = new AtomicIntegerThread(latch_1, latch_n, loopCount);
  thread.start();
 }
 long startNano = System.nanoTime();
 // 讓其他期待的線程同一開端
 latch_1.countDown();
 // 期待其他線程履行完
 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 {
 // 創立的線程數目
 int threadCount = 100;
 // 其他從屬線程外部輪回若干次
 int loopCount = 10000600;
 // 掌握從屬線程的幫助對象;(其他await的線程先等著主線程喊開端)
 CountDownLatch latch_1 = new CountDownLatch(1);
 // 掌握主線程的幫助對象;(主線程等著一切從屬線程都運轉終了再持續)
 CountDownLatch latch_n = new CountDownLatch(threadCount);
 // 創立並啟動其他從屬線程
 for (int i = 0; i < threadCount; i++) {
  Thread thread = new IntegerThread(latch_1, latch_n, loopCount);
  thread.start();
 }
 long startNano = System.nanoTime();
 // 讓其他期待的線程同一開端
 latch_1.countDown();
 // 期待其他線程履行完
 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機上的履行成果相似以下:

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

從中可以看出, AtomicInteger操作 與 int操作的效力年夜致相差在50-80倍高低,固然,int很不用耗時光,這個比較只是供給一個參照。

假如肯定是單線程履行,那應當應用 int; 而int在多線程下的操作履行的效力照樣蠻高的, 10億次只花了1.5秒鐘;

 (假定CPU是 2GHZ,雙核4線程,實際最年夜8GHZ,則每秒實際上有80億個時鐘周期,

 10億次Java的int增長消費了1.5秒,即 120億次運算, 算上去每次輪回消費CPU周期 12個;

小我認為效力不錯, C 說話也應當須要4個以上的時鐘周期(斷定,履行外部代碼,自增斷定,跳轉)

 條件是: JVM和CPU沒有停止保守優化.

)

而 AtomicInteger 效力其實也不低,10億次消費了80秒, 那100萬次年夜約也就是千分之一,80毫秒的模樣.

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved