興味深い同時concurrencyhashMapコード

2842 ワード

package concurrencyTest;

import java.util.Iterator;
import java.util.concurrent.ConcurrentHashMap;

public class ConcurrencyTest2 {

	public static Object mutex = new Object() ;
	/**
	 * @param args
	 */
	public static void main(String[] args) {
		ConcurrentHashMap  map = new ConcurrentHashMap() ;
		for(int i=0;i<100000 ; i++)
			map.put(i, i+111111) ;
		
		long start = System.currentTimeMillis() ;
		Thread t1 = new Thread(new Producer(map)) ;
		Thread t2 = new Thread(new Consumer(map)) ;
		
		try {
			Thread.sleep(200) ;
			t1.start(); 
			t2.start();
			
			t1.join() ;
			t2.join();
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
		System.out.println("Read last : " + (System.currentTimeMillis() - start) + " ms" + " shareMap : " + map.size());
	}
}

class Producer implements Runnable {
	ConcurrentHashMap  sharemap ;
    int num = 0 ;
    public static volatile boolean end = false; 
	
	public Producer(ConcurrentHashMap map) {
		sharemap = map ;
	}
	
	@Override
	public void run() {
		try {
		 int i =50000 ;
		 while(i<1000000) {
			 add(i) ;
			 i++ ;
			 if(i==120000)  
				 Thread.sleep(1000) ;
		 }
		 end = true ;	
		 System.out.println(Thread.currentThread().getName() + " add " + (i - 50000) + " elements! ShareMap size: " + sharemap.size() );
		} catch (Exception e) {
			e.printStackTrace() ;
		}
	}

	  public void add(int item) {  
		  synchronized (ConcurrencyTest2.mutex) {
			  if(!sharemap.containsKey(item)) {
				  sharemap.putIfAbsent(item, item + 111111) ;
			  } else {
				  sharemap.put(item, sharemap.get(item) + 222222) ; 
			  }
		}
	  }
}

class Consumer implements Runnable {
	ConcurrentHashMap  sharemap ;
    int num = 0 ;
	
	public Consumer(ConcurrentHashMap map) {
		sharemap = map ;
		it = sharemap.values().iterator();
	}
	
	@Override
	public void run() {
		 Integer i = poll(); 
		 while(!Producer.end) {
			 if((i = poll())!=null) {
				 num++ ;
			 } else {
				 it = sharemap.values().iterator();
				 System.out.println("wait poll num: " + num + " ShareMap size: "+ sharemap.size());
			 }
		 }
		 System.out.println(Thread.currentThread().getName() + " poll " + num + " elements! ShareMap size: " + sharemap.size() );
	}
	
	Iterator it;

	public Integer poll() {
		  synchronized (ConcurrencyTest2.mutex) {
			     if (sharemap.size() > 0 && it!=null && it.hasNext()) {
			         Integer m = it.next();
			         it.remove();
			         return m;
			       } else {
			         return null;
			       }		  
		  }
	}
}

生産しながら、消費して、性能が悪いですね!