一、原码-反码-补码
二、常用的位运算
与(&):相同位上,都为1,结果才是1
5 & 3 = 1 (101 & 011 = 001)登录后复制
或(|):相同位上,只要有一个1,结果则为1
5 | 3 = 7 ( 101 | 011 = 111)登录后复制
异或(^) :相同位上,不同则为1,相同则为0
5 ^ 3 = 0 (101 ^ 011 = 110)登录后复制
取反(~) :1变0,0变1
~5 = - 6登录后复制
左移(<<) :低位补0
正数,在不溢出的情况下,每左移一位相当于数值乘以2,7 << 1 = 14登录后复制
右移(>>) :正数高位补0,负数高位补1
在不溢出的情况下,每右移一位相当于除以2并向下取整,7 >> 1 = 3登录后复制
无符号右移(>>>) :高位补0
Integer.bitCount()登录后复制
public interface UserOptType{long BASE_INFO = 1;long VIP_INFO = 1 << 1;long FANS_INFO = 1 << 2;long ATTENTION_INFO = 1 << 3;long MODEL_INFO = 1 << 4;long REAL_NAME_INFO = 1 << 5;}public class UserService{public Object getUserInfo(String userId,long optType){Object result = new Object();if ( optType & UserOptType.BASE_INFO > 0 ){setBaseInfo(userId,result);}if ( optType & UserOptType.VIP_INFO > 0 ){setVipInfo(userId,result);}// ......}}登录后复制
public boolean isEven(int input){return input % 2 == 0;}登录后复制
public boolean isEven(int input){return input & 1 == 0;}登录后复制
3.5 一个字段表示多种含义
private final AtomicInteger ctl = new AtomicInteger(ctlOf(RUNNING, 0));// 低29位表示线程数,因此最大线程数为 2^29 -1,大约500多万// 实际应用中,计算机是不可能创建这么多线程的// 以JVM为例,一个线程占用256K (-Xss),8G内存,最多也就创建 4 * 8 * 1024private static final int COUNT_BITS = Integer.SIZE - 3;private static final int CAPACITY = (1 << COUNT_BITS) - 1;// 当前线程池的运行状态,存储在高位// 用负数来表示运行中private static final int RUNNING = -1 << COUNT_BITS;private static final int SHUTDOWN = 0 << COUNT_BITS;private static final int STOP = 1 << COUNT_BITS;private static final int TIDYING = 2 << COUNT_BITS;private static final int TERMINATED = 3 << COUNT_BITS;// 对控制字段的解包和打包方法// 求解出当前的运行状态,当前的线程数private static int runStateOf(int c) { return c & ~CAPACITY; }private static int workerCountOf(int c) { return c & CAPACITY; }private static int ctlOf(int rs, int wc) { return rs | wc; }// 直接使用CAS增加线程数private boolean compareAndIncrementWorkerCount(int expect) {return ctl.compareAndSet(expect, expect + 1);}private boolean compareAndDecrementWorkerCount(int expect) {return ctl.compareAndSet(expect, expect - 1);}登录后复制
位运算是直接对整数在内存中的二进制位进行操作,包括与(&),或(|),异或(^),取反(~),左移(<<),右移(>>)和无符号右移(>>>)。这些运算常用于开关类场景,如状态开关和签到记录。在Java的ThreadPoolExecutor线程池中,ctl字段用位运算高效地表示线程池状态和线程数量。此外,位运算还用于HashMap的哈希计算,通过与运算实现数据分表等。
1364

被折叠的 条评论
为什么被折叠?



