Java中的位操作使用举例

本文的目的不是为了阐述位操作的原理,而是发现在工作中有些同学清楚位操作,但是不知道什么时候使用位操作。以下列举两个例子简单说明我们可以使用到位操作的场景,但不一定符合实际业务场景,仅供参考。

1、给40亿个int型的正整数,没排过序,然后再给一个数,如何快速判断这个数是否在那40亿个数当中。(此题根据腾讯的一道面试题改编)

public class A {
	
	long nSize = 4000000000L;
	int bSize = (int)(nSize / 8);
	byte[] bArray = new byte[bSize]; //正好有40亿个位,每个位代表一个数字

	/**
	 * 将40亿个数放入到数组中,把每个数字对应的位的值由0变为1
	 * 这里只是为了把数组填满而已
	 */
	public void init() {
		for (long i = 1; i <= nSize; i++) {
			
			if (i % 10 == 0) { //为了让一些数字在bArray中不存在
				continue;
			}
			
			byte mod = (byte) (i % 8);
			int div = (int) (i / 8);
			int index = (int)(mod == 0 ? div - 1 : div);
			
			bArray[index] = (byte) (bArray[index] | (1 << mod));
		}
	}
	
	/**
	 * 在40亿个数当中查找一个数字是否存在
	 * 如果n对应的位在bArray的值是1,则表明数字存在
	 * 
	 * @param n 要查找的数
	 * @return 如果要查找的数在40亿中存在,返回true,否则返回false
	 */
	public boolean find(long n) {
		
		byte mod = (byte) (n % 8);
		int div = (int) (n / 8);
		
		int index = (int)(mod == 0 ? div - 1 : div);

		return (bArray[index] & (1 << mod)) > 0; 
	}
	
	public static void main(String args[]) {
		
		A a = new A();
		a.init();
		System.out.println(a.find(111));
		System.out.println(a.find(1000));
	}
	
}

2、假设一个订单有三组状态需要记录,分别是付款状态、发货状态、签收状态,我们可以在类里用三个属性来表示(一般来说都是这么做的),这里我们用另外一种方式用一个属性将所有状态表示出来(这么做之前要仔细考虑是否符合业务需求)

public class Order {

	//订单状态,将三组订单状态用这个值后三位表示
	private byte status = 0x00;
	
	//付款
	public void pay() {
		this.status |= Status.已付款.getValue();
	}
	
	//发货
	public void send() {
		this.status |= Status.已发货.getValue();
	}
	
	//签收
	public void receive() {
		this.status |= Status.已签收.getValue();
	}
	
	//获取已付款状态
	public boolean hasPaid() {
		return (this.status & Status.已付款.getValue()) > 0;
	}

	//获取已发货状态
	public boolean hasSent() {
		return (this.status & Status.已发货.getValue()) > 0;
	}

	//获取已签收状态
	public boolean hasReceived() {
		return (this.status & Status.已签收.getValue()) > 0;
	}
	
	//main()
	public static void main(String args[]) {
		
		Order order = new Order();
		order.send();
		
		System.out.println(order.hasPaid());
		System.out.println(order.hasSent());
		System.out.println(order.hasReceived());
	}
}

//订单状态枚举类
enum Status {
	
	已付款((byte)0x01),
	已发货((byte)0x02),
	已签收((byte)0x04);
	
	private Status(byte b) {
		this.value = b;
	}
	
	private byte value;

	public byte getValue() {
		return value;
	}
	
}



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值