29. Divide Two Integers

本文介绍了一种不使用乘、除和取余运算符实现整数除法的方法。通过位操作逐步逼近商的值,并讨论了溢出处理及符号位的处理方式。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

Divide two integers without using multiplication, division and mod operator.

If it is overflow, return MAX_INT.


基本思想用例子说明,例如327/6=54,首先找出327最多够减去6的左移多少位,6<<5=192,那就用327-192=135,

最多能够减去6的左移5位,剩下135,商就加上1<<5=32,然后135再做迭代处理,6<<4=96,135-96=39,商+=(1<<4=16),

6<<2=24,39-24=15,商+=(1<<2=4),6<<1=12,15-12=3,商+=(1<<1=2),剩下的3不够减去6的左移任何一位,停止了。

商的符号可以通过将被除数和除数的符号位异或得到,然后化为无符号处理,最后添上符号。

整数最小-2148473648和最大2147483647数值不一样,防止溢出需要特别处理,为了简便就直接上long吧,

就是因为坚持使用int,代码才把简单的逻辑都搞乱了。。。QAQ


public static int divide(int dividend, int divisor)
	{
		if(dividend==0)
			return 0;
		if(dividend==Integer.MIN_VALUE&&divisor==-1)
			return Integer.MAX_VALUE;
		
		int retnegative=(dividend>>31)^(divisor>>31);
		int add=0;
		
		
		if((divisor>>31&0x1)==1)
			divisor=-divisor;
		
		if(dividend==Integer.MIN_VALUE)
		{
			dividend=Integer.MAX_VALUE-divisor+1;
			add++;
		}
		
		if((dividend>>31&0x1)==1)
			dividend=-dividend;
		
		
		
		if(divisor>=Integer.MAX_VALUE>>1)
		{
			int ret= dividend-divisor>=0?1:0;
			
			if(ret>0)
			{
				dividend-=divisor;
				dividend+=add;
				ret=dividend-divisor>=0?ret+1:ret;
			}
			
			ret+=add;
			if(retnegative!=0)
				ret=-ret;
			return ret;
		}
		
		int ret=0;
		int i=0;
		for(;(divisor<<i)<(Integer.MAX_VALUE>>1);i++)
			if(dividend-(divisor<<i)<0)
				break;
		
		if(i==0)
			ret=0;
		else {
			ret+=1<<(i-1);
			int remain=dividend-=divisor<<(i-1);
			ret+=divide(remain, divisor);
		}
		
		ret+=add;
		
		if(retnegative!=0)
			ret=-ret;
		
		return ret;
		
	}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值