每日一题「整数除法」

Posted 陈皮的JavaLib

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了每日一题「整数除法」相关的知识,希望对你有一定的参考价值。

我是陈皮,一个在互联网 Coding 的 ITer,个人微信公众号「陈皮的JavaLib」关注第一时间阅读最新技术文章。

文章目录

题目

输入2个 int 型整数,将它们进行除法计算并返回商,要求不得使用乘号、除号及求余符号。当发生溢出时,返回最大的整数值。假设除数不为0。例如,输入15和2,输出15/2的结果,即7。

分析

限制了不可以使用除法,乘法,和求余运算,那么可以使用减法来实现除法。

例如15/2,不断地从15里减去2,当减去7个2之后余数是1,余数不能再减去2,所以15/2的商是7。使用一个循环即可实现这个过程。

不过,但当被除数很大但除数很小时,减法操作执行的次数会很多。例如,当被除数为 int 类型的最大值 2^31 - 1,除数为1时,减1操作次数为 2^31 - 1 次。当除数为2时,减2操作次数也要 2^30 次左右。这样会导致算法速度很慢。

所以我们需要优化,如果被除数大于除数时,判断被除数是否大于除数的2倍,如果是,再判断是否4倍,8倍…,直到最多2n倍。然后将被除数减去2n个除数,2n的值累加到总的减次数中,将剩余的被除数继续重复以上操作,直到剩余的被除数小于除数。因为每次将除数翻倍,所以时间复杂度是O(logn)。

因为被除数和除数都有可能是负数,为方便计算,需要先将它们都转为同符号的整数,计算出结果后,再进行对商调整符号。如果将负数都调整为正数,有可能会发生溢出,例如负数-231,但是正数最大值是231-1。所以我们选择将正数转为负数,对两个负数进行除法求商,最后再对商的符号进行调整。

实现

package com.chenpi;

/**
 * @author 陈皮
 * @version 1.0
 * @description
 * @date 2022/3/17
 */
public class ChenPi 

  public static void main(String[] args) 
    ChenPi inst = new ChenPi();
    int dividend = -18;
    int divisor = 3;
    System.out.println(inst.divide(dividend, divisor));
  

  public int divide(int dividend, int divisor) 

    // 这种情况会发生溢出
    if (dividend == Integer.MIN_VALUE && divisor == -1) 
      return Integer.MAX_VALUE;
    

    // 记录负号的个数
    int negativeCount = 2;

    // 被除数如果为正数转为负数
    if (dividend > 0) 
      dividend = -dividend;
      negativeCount--;
    

    // 除数如果为正数转为负数
    if (divisor > 0) 
      divisor = -divisor;
      negativeCount--;
    

    // 商
    int result = 0;

    // 被除数小于除数时(因为它们都是负数),重复
    while (dividend <= divisor) 
      // 记录最大的|除数*2n|绝对值
      int timesValue = divisor;
      // 减去除数的次数
      int times = 1;
      // 最小值是-2^31,0xc0000000是-2^30,避免timesValue是-2^31时,timesValue + timesValue发生溢出
      while (timesValue >= 0xc0000000 && dividend <= timesValue + timesValue) 
        times += times;
        timesValue += timesValue;
      
      result += times;
      dividend -= timesValue;
    

    // 商符号调整
    return negativeCount == 1 ? -result : result;
  


输出结果

-6

本次分享到此结束啦~~

如果觉得文章对你有帮助,点赞、收藏、关注、评论,您的支持就是我创作最大的动力!

以上是关于每日一题「整数除法」的主要内容,如果未能解决你的问题,请参考以下文章

每日一题「整数除法」

每日一题「整数除法」

JAVA自除数——力扣每日一题(2022.03.31)

JAVA自除数——力扣每日一题(2022.03.31)

JAVA自除数——力扣每日一题(2022.03.31)

JAVA自除数——力扣每日一题(2022.03.31)