How to set initial size for HashMap

1. Requirements of Alibaba code specifications

Insert image description here

2. When scanning using Alibaba plug-in

Insert image description here
Insert image description hereInsert image description here
Insert image description here

3. Source code

3.1 When initialization does not set the size

Map<Integer, BigDecimal> staffDidiMap = new HashMap<>();
Insert image description here
Insert image description here

3.2 When initializing the size

Map<Integer, BigDecimal> staffDidiMap = new HashMap<>(16);
Insert image description here
Insert image description here
Insert image description here

@Test
	public void caffineTest() {
    
    
		System.out.println(1 << 30);
	}
result: 1073741824

this.threshold = tableSizeFor(initialCapacity);
Insert image description here

@Test
	public void caffineTest() {
    
    
		int cap = 16;
		int n = cap - 1;
		n |= n >>> 1;
		n |= n >>> 2;
		n |= n >>> 4;
		n |= n >>> 8;
		n |= n >>> 16;
		int result = (n < 0) ? 1 : (n >= 1073741824) ? 1073741824 : n + 1;
		System.out.println(result);
	}
result: 16

//TODO source code part needs to be improved

4. Test

@SpringBootTest
public class CaffineTest {
    
    

	@Test
	public void caffineTest() throws InterruptedException {
    
    
		test1();
		test2();
		test3();
		test4();
		test5();
	}

	void test1() throws InterruptedException {
    
    
		int aHundredMillion = 10000000;
		Map<Integer, Integer> map = new HashMap<>();
		long s1 = System.currentTimeMillis();
		for (int i = 0; i < aHundredMillion; i++) {
    
    
			map.put(i, i);
		}
		long s2 = System.currentTimeMillis();
		System.out.println("未初始化容量,耗时 : " + (s2 - s1));
		map.clear();
		Thread.sleep(5000);
	}

	void test2() throws InterruptedException {
    
    
		int aHundredMillion = 10000000;
		Map<Integer, Integer> map1 = new HashMap<>(aHundredMillion / 2);
		long s5 = System.currentTimeMillis();
		for (int i = 0; i < aHundredMillion; i++) {
    
    
			map1.put(i, i);
		}
		long s6 = System.currentTimeMillis();
		System.out.println("初始化容量5000000,耗时 : " + (s6 - s5));
		map1.clear();
		Thread.sleep(5000);
	}

	void test3() throws InterruptedException {
    
    
		int aHundredMillion = 10000000;
		Map<Integer, Integer> map2 = new HashMap<>(aHundredMillion);
		long s3 = System.currentTimeMillis();
		for (int i = 0; i < aHundredMillion; i++) {
    
    
			map2.put(i, i);
		}
		long s4 = System.currentTimeMillis();
		System.out.println("初始化容量为10000000,耗时 : " + (s4 - s3));
		map2.clear();
		Thread.sleep(5000);
	}

	void test4() throws InterruptedException {
    
    
		int aHundredMillion = 10000000;
		// 按照阿里巴巴规范   initialCapacity = (需要存储的元素个数 / 负载因子) + 1。注意负载因子(即 loader factor)默认 为 0.75
		int initial = (int) (aHundredMillion / 0.75F + 1F);
		Map<Integer, Integer> map3 = new HashMap<>(initial);
		long s7 = System.currentTimeMillis();
		for (int i = 0; i < aHundredMillion; i++) {
    
    
			map3.put(i, i);
		}
		long s8 = System.currentTimeMillis();
		System.out.println("初始化容量为" + initial + "耗时" + (s8 - s7));
		map3.clear();
		Thread.sleep(5000);
	}

	void test5() throws InterruptedException {
    
    
		int aHundredMillion = 10000000;
		// 初始化16
		Map<Integer, Integer> map4 = new HashMap<>(16);
		long s9 = System.currentTimeMillis();
		for (int i = 0; i < aHundredMillion; i++) {
    
    
			map4.put(i, i);
		}
		long s10 = System.currentTimeMillis();
		System.out.println("初始化容量为" + 16 + "耗时" + (s10 - s9));
		map4.clear();
		Thread.sleep(5000);
	}
}

Result:
Insert image description here
Ten million pieces of data are inserted into the map each time.
Method 1: Not initialized,
time consuming 3995. Method 2: Initialization to 5 million,
time consuming 2345. Method 3: Initialization to 10 million
, time consuming 261. Method 4: Initialization according to Alibaba specifications, time consuming 192.
Method 5: Initialization 16, time consuming 182.

! ! !
After many tests, it can be concluded that the worst performance is uninitialized, the most efficient and stable one is according to Alibaba specifications initialCapacity = (需要存储的元素个数 / 负载因子) + 1。注意负载因子(即 loader factor)默认 为 0.75, then 16 and finally according to the size of the assigned size.

Insert image description here
Insert image description hereInsert image description here
Insert image description here

appendix

1. Why does Alibaba recommend that the capacity of HashMap needs to be specified when initializing it?

Guess you like

Origin blog.csdn.net/Blue_Pepsi_Cola/article/details/131810014