在HashMap的tableSizeFor方法中这段代码很有意思,乍一看有点懵。
/**
* Returns a power of two size for the given target capacity.
*/
static final int tableSizeFor(int cap) {
int n = cap - 1;
n |= n >>> 1;
n |= n >>> 2;
n |= n >>> 4;
n |= n >>> 8;
n |= n >>> 16;
return (n < 0) ? 1 : (n >= MAXIMUM_CAPACITY) ? MAXIMUM_CAPACITY : n + 1;
}
首先说这个代码是干嘛的:是为了得到一个大于获等于他的2的幂并返回;
首先看这段迷惑代码:
n |= n >>> 1;
n |= n >>> 2;
n |= n >>> 4;
n |= n >>> 8;
n |= n >>> 16;
这段代码的目的是把n
的二进制数中的0
置为1
,比如2
是10
经过处理以后变成11
,什么原理呢?
假设传进来一个数的二进制是100001001;
n |= n >>> 1;
在这里处理之后是110001101,这一步可以这样理解,
如果你是1,那么把你的下一位变成1,那么是不是有1的地方会存在两个1,
这也就解释了为什么下一行要无符号右移2,依此类推1,2,4,8,16,下下次直接右移4.
n |= n >>> 2;
在这里处理之后是111101111
n |= n >>> 4;
在这里处理之后是111111111
n |= n >>> 8;
n |= n >>> 16;
处理完之后,必然是全1
,也就是2幂-1,那么返回n+1;
int n = cap - 1;
这一步是为了防止传入的cap
本来就是2
的幂,结果处理成2n+1了。