【leetcode-模拟】加一/二进制求和/各位相加/字符串相乘/两数相除

加一

给定一个由 整数 组成的 非空 数组所表示的非负整数,在该数的基础上加一。
最高位数字存放在数组的首位, 数组中每个元素只存储单个数字。
你可以假设除了整数 0 之外,这个整数不会以零开头。

示例 1:
输入:digits = [1,2,3]
输出:[1,2,4]
解释:输入数组表示数字 123。

示例 2:
输入:digits = [4,3,2,1]
输出:[4,3,2,2]
解释:输入数组表示数字 4321。

示例 3:
输入:digits = [0]
输出:[1]

模拟

class Solution {
    public int[] plusOne(int[] digits) {
        int len = digits.length;
        for (int i = len - 1; i >= 0; i--) {
            digits[i]++;
            digits[i] %= 10;
            if (digits[i] != 0) 
                return digits;
        }
        digits = new int[len + 1];
        digits[0] = 1;
        return digits;
    }
}

二进制求和

给你两个二进制字符串,返回它们的和(用二进制表示)。
输入为 非空 字符串且只包含数字 1 和 0。

示例 1:
输入: a = “11”, b = “1”
输出: “100”

示例 2:
输入: a = “1010”, b = “1011”
输出: “10101”

模拟

class Solution {
    public String addBinary(String a, String b) {
        int aLen = a.length(), bLen = b.length();
        StringBuffer result = new StringBuffer();

        int n = Math.max(aLen, bLen), carry = 0;
        for (int i = 0; i < n; ++i) {
            carry += i < aLen ? (a.charAt(aLen - 1 - i) - '0') : 0;
            carry += i < bLen ? (b.charAt(bLen - 1 - i) - '0') : 0;
            result.append(carry % 2);
            carry /= 2;
        }
        result.append(carry == 1 ? carry : "");
        return result.reverse().toString();
    }
}

各位相加

给定一个非负整数 num,反复将各个位上的数字相加,直到结果为一位数。

示例:
输入: 38
输出: 2
解释: 各位相加的过程为:3 + 8 = 11, 1 + 1 = 2。 由于 2 是一位数,所以返回 2。

迭代法

class Solution {
    public int addDigits(int num) {
        while (num > 9) {
            int tmp = 0;
            while (num > 0) {
                tmp += num % 10;
                num /= 10;
            }
            num = tmp;
        }
        return num;
    }
}

数学法

数根是将一正整数的各个位数相加(即横向相加),若加完后的值大于10的话,则继续将各位数进行横向相加直到其值小于十为止,或是,将一数字重复做数字和,直到其值小于十为止,则所得的值为该数的数根。
在这里插入图片描述
在这里插入图片描述

class Solution {
    public int addDigits(int num) {
        return (num - 1) % 9 + 1;
    }
}

字符串相乘

给定两个以字符串形式表示的非负整数 num1 和 num2,返回 num1 和 num2 的乘积,它们的乘积也表示为字符串形式。

示例 1:
输入: num1 = “2”, num2 = “3”
输出: “6”

示例 2:
输入: num1 = “123”, num2 = “456”
输出: “56088”

说明:
num1 和 num2 的长度小于110。
num1 和 num2 只包含数字 0-9。
num1 和 num2 均不以零开头,除非是数字 0 本身。
不能使用任何标准库的大数类型(比如 BigInteger)或直接将输入转换为整数来处理。

数组存储

class Solution {
    public String multiply(String num1, String num2) {
        if (num1.equals("0") || num2.equals("0"))
            return "0";
        
        int len1 = num1.length(), len2 = num2.length();
        int[] result = new int[len1 + len2 + 1];
        for (int i = 0; i < len1; i++) {
            int x = num1.charAt(len1 - i - 1) - '0';
            for (int j = 0; j < len2; j++) {
                int y = num2.charAt(len2 - j - 1) - '0';
                result[i + j] += x * y;
            }
        }
        StringBuilder s = new StringBuilder();
        for (int i = 0; i < len1 + len2; i++) {
            s.insert(0, result[i] % 10);
            result[i + 1] += result[i] / 10;
        }
        while (s.length() != 1 && s.charAt(0) == '0') {
            s.delete(0, 1);
        }
        return s.toString();
    }
}

两数相除

给定两个整数,被除数 dividend 和除数 divisor。将两数相除,要求不使用乘法、除法和 mod 运算符。
返回被除数 dividend 除以除数 divisor 得到的商。
整数除法的结果应当截去(truncate)其小数部分,例如:truncate(8.345) = 8 以及 truncate(-2.7335) = -2

示例 1:
输入: dividend = 10, divisor = 3
输出: 3

示例 2:
输入: dividend = 7, divisor = -3
输出: -2

示例 3:
输入: dividend = -2147483648, divisor = -1
输出: 2147483647

示例 4:
输入: dividend = -2147483648, divisor = 2
输出: -1073741824

示例 5:
输入: dividend = 2147483647, divisor = 2
输出: 1073741823

模拟

由于要考虑边界问题,因此若将 dividend 和 divisor,都变成正数可能会溢出,所以将二者都变成负数。

class Solution {
    public int divide(int dividend, int divisor) {
        boolean sign = (dividend > 0) ^ (divisor > 0);
        dividend = (dividend > 0) ? -dividend : dividend;
        divisor = (divisor > 0) ? -divisor : divisor;
        int result = 0;

        int min = Integer.MIN_VALUE >> 1;
        while(dividend <= divisor) {
            int temp_result = -1;
            int temp_divisor = divisor;
            while(dividend <= (temp_divisor << 1)) {
                if(temp_divisor <= min)
                    break;
                temp_result = temp_result << 1;
                temp_divisor = temp_divisor << 1;
            }
            dividend = dividend - temp_divisor;
            result += temp_result;
        }

        if (!sign) {
            if(result <= Integer.MIN_VALUE) 
                return Integer.MAX_VALUE;
            result = -result;
        }
        return result;
    }
}

字符串相加

给定两个字符串形式的非负整数 num1 和num2 ,计算它们的和。

提示:

  • num1 和num2 的长度都小于 5100
  • num1 和num2 都只包含数字 0-9
  • num1 和num2 都不包含任何前导零
  • 你不能使用任何內建 BigInteger 库, 也不能直接将输入的字符串转换为整数形式

模拟

class Solution {
    public String addStrings(String num1, String num2) {
        char[] chars1 = num1.toCharArray(), chars2 = num2.toCharArray();
        int i = chars1.length - 1, j = chars2.length - 1;

        int len = Math.max(chars1.length, chars2.length) + 1;
        char[] result = new char[len];
        int carry = 0, index = len - 1;
        while (i >= 0 || j >= 0) {
            int x = i < 0 ? 0 : chars1[i--] - '0';
            int y = j < 0 ? 0 : chars2[j--] - '0';
            int sum = x + y + carry;
            carry = sum / 10;
            result[index--] = (char)(sum % 10 + '0');
        }

        if (carry == 0)
            return new String(result, 1, len - 1);
        result[0] = '1';
        return new String(result);
    }
}
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值