public ConcurrentHashMap(int initialCapacity) {
if (initialCapacity < 0)
throw new IllegalArgumentException();
int cap = ((initialCapacity >= (MAXIMUM_CAPACITY >>> 1)) ?
MAXIMUM_CAPACITY :
tableSizeFor(initialCapacity + (initialCapacity >>> 1) + 1));
this.sizeCtl = cap;
}
tableSizeFor 的道理我都懂,这和 hashmap 一样,但这里为啥不是直接传递 initialCapacity 给 tableSizeFor 呢?
我把两种情况对比了一下,发现好像也没啥规律啊?
1 ==> 1 1 ==> 2 ==> 2
2 ==> 2 2 ==> 4 ==> 4
3 ==> 4 3 ==> 5 ==> 8
4 ==> 4 4 ==> 7 ==> 8
5 ==> 8 5 ==> 8 ==> 8
6 ==> 8 6 ==> 10 ==> 16
7 ==> 8 7 ==> 11 ==> 16
8 ==> 8 8 ==> 13 ==> 16
9 ==> 16 9 ==> 14 ==> 16
10 ==> 16 10 ==> 16 ==> 16
11 ==> 16 11 ==> 17 ==> 32
12 ==> 16 12 ==> 19 ==> 32
13 ==> 16 13 ==> 20 ==> 32
14 ==> 16 14 ==> 22 ==> 32
15 ==> 16 15 ==> 23 ==> 32
16 ==> 16 16 ==> 25 ==> 32
17 ==> 32 17 ==> 26 ==> 32
18 ==> 32 18 ==> 28 ==> 32
19 ==> 32 19 ==> 29 ==> 32
20 ==> 32 20 ==> 31 ==> 32
21 ==> 32 21 ==> 32 ==> 32
22 ==> 32 22 ==> 34 ==> 64
23 ==> 32 23 ==> 35 ==> 64
24 ==> 32 24 ==> 37 ==> 64
25 ==> 32 25 ==> 38 ==> 64
26 ==> 32 26 ==> 40 ==> 64
27 ==> 32 27 ==> 41 ==> 64
28 ==> 32 28 ==> 43 ==> 64
29 ==> 32 29 ==> 44 ==> 64
30 ==> 32 30 ==> 46 ==> 64
31 ==> 32 31 ==> 47 ==> 64
32 ==> 32 32 ==> 49 ==> 64
33 ==> 64 33 ==> 50 ==> 64
34 ==> 64 34 ==> 52 ==> 64
35 ==> 64 35 ==> 53 ==> 64
36 ==> 64 36 ==> 55 ==> 64
1
luckyrayyy 2020-07-08 23:24:57 +08:00
虽然我没记住你的 ID,但是一看问题就有预感是谁提问的....老哥加油
|
2
sujin190 2020-07-08 23:28:12 +08:00
内存对齐,还有现在大部分内存分配管理器都是 2 的倍数分配的,不这样处理那就白白浪费内存了
|
3
amiwrong123 OP @luckyrayyy
是因为我经常发源码讨论的帖子吗😂 |
4
amiwrong123 OP @sujin190
可是直接传递 initialCapacity 给 tableSizeFor,结果也是 2 的幂啊 |
5
AmmeLid 2020-07-09 00:26:47 +08:00 via iPhone
2==>2,依照你的算法设置容量为 2 的话,放入第二个元素的时候就超过负载触发一次扩容了吧
|
6
amiwrong123 OP @AmmeLid
好吧,是你这个意思。有点像是除以 0.75 再向上取整的感觉,不完全和 除以 0.75 再向上取整 一样 |
7
Hyseen 2020-07-09 08:56:52 +08:00 3
这是个 bug,在 11 中已经修复了
https://bugs.openjdk.java.net/browse/JDK-8202422 |
8
sujin190 2020-07-09 09:39:15 +08:00
@amiwrong123 #4 不是 2 的幂,你可以查一下大部分分配器的实现,大部分都是 2 4 8 16 32 这样分配的,倍数,虽然会浪费一些内存,但是内存碎片少,分配管理效率高
|
9
amiwrong123 OP @Hyseen
好吧,原来如此。。bug 修正后,最起码两种构造器结果一样了 |