首页 > 试题广场 >

Powerful Calculator

[编程题]Powerful Calculator
  • 热度指数:6539 时间限制:C/C++ 1秒,其他语言2秒 空间限制:C/C++ 64M,其他语言128M
  • 算法知识视频讲解
    Today, facing the rapid development of business, SJTU recognizes that more powerful calculator should be studied, developed and appeared in future market shortly. SJTU now invites you attending such amazing research and development work.     In most business applications, the top three useful calculation operators are Addition (+), Subtraction (-) and Multiplication (×) between two given integers. Normally, you may think it is just a piece of cake. However, since some integers for calculation in business application may be very big, such as the GDP of the whole world, the calculator becomes harder to develop.     For example, if we have two integers 20 000 000 000 000 000 and 4 000 000 000 000 000, the exact results of addition, subtraction and multiplication are:     20000000000000000 + 4000000000000000 = 24 000 000 000 000 000     20000000000000000 - 4000000000000000 = 16 000 000 000 000 000     20000000000000000 × 4000000000000000 = 80 000 000 000 000 000 000 000 000 000 000     Note: SJTU prefers the exact format of the results rather than the float format or scientific remark format. For instance, we need "24000000000000000" rather than 2.4×10^16.     As a programmer in SJTU, your current task is to develop a program to obtain the exact results of the addition (a + b), subtraction (a - b) and multiplication (a × b) between two given integers a and b.

输入描述:
   Each case consists of two separate lines where the first line gives the integer a and the second gives b (|a| <10^400 and |b| < 10^400).


输出描述:
    For each case, output three separate lines showing the exact results of addition (a + b), subtraction (a - b) and multiplication (a × b) of that case, one result per lines.
示例1

输入

20000000000000000
4000000000000000

输出

24000000000000000
16000000000000000
80000000000000000000000000000000
#include <iostream>
#include <cstdio>
#include <cstring>
#include <string>
using namespace std;

struct bign {
    int d[1010], len;
    bool tag;
    bign() {
        memset(d, 0, sizeof d);
        len = 0;
        tag = true;
    }
};
bign change(string s) {
    bign a;
    if(s[0] == '-') {
        a.tag = false;
        s.erase(s.begin());
    }
    for(int i = s.size() - 1; i >= 0; i--) {
        a.d[a.len++] = s[i] - '0';
    }
    return a;
}
int cmp(bign a, bign b) {
    if(a.len > b.len) return 1;
    else if(a.len < b.len) return -1;
    else {
        for(int i = a.len - 1; i >= 0; i--) {
            if(a.d[i] > b.d[i]) return 1;
            else if(a.d[i] < b.d[i]) return -1;
        }
    }
    return 0;
}
bign add(bign a, bign b) {
    bign c; int carry = 0;
    for(int i = 0; i < a.len || i < b.len; i++) {
        int temp = a.d[i] + b.d[i] + carry;
        c.d[c.len++] = temp % 10;
        carry = temp / 10;
    }
    if(carry) c.d[c.len++] = carry;
    return c;
}
bign sub(bign a, bign b) {
    bign c;
    for(int i = 0; i < a.len || i < b.len; i++) {
        if(a.d[i] < b.d[i]) {
            a.d[i] += 10;
            a.d[i + 1]--;
        }
        c.d[c.len++] = a.d[i] - b.d[i];
    }
    while(c.len - 1 >= 1 && c.d[c.len - 1] == 0) c.len--;
    return c;
}
bign mul(bign a, int b) {
    bign c; int carry = 0;
    for(int i = 0; i < a.len; i++) {
        int temp = a.d[i] * b + carry;
        c.d[c.len++] = temp % 10;
        carry = temp / 10;
    }
    while(carry) {
        c.d[c.len++] = carry % 10;
        carry /= 10;
    }
    return c;
}
bign addZero(bign a, int n) {
    bign c;
    for(int i = 0; i < n; i++) {
        c.d[c.len++] = 0;
    }
    for(int i = 0; i < a.len; i++) {
        c.d[c.len++] = a.d[i];
    }
    return c;
}
bign MUL(bign a, bign b) {
    bign c;
    for(int i = 0; i < b.len; i++) {
        bign t = addZero(mul(a, b.d[i]), i);
        c = add(c, t);
    }
    return c;
}
void print(bign &a) {
    if(a.tag == false) printf("-");
    for(int i = a.len - 1; i >= 0; i--) {
        printf("%d", a.d[i]);
    }
    printf("\n");
}
int main() {
    string s1, s2;
    while(cin >>s1 >>s2) {
        bign a = change(s1), b = change(s2), sum, diff, c, d, e;
        sum = add(a, b); diff = cmp(a, b) < 0 ? sub(b, a) : sub(a, b);
        bool eTag = true;
        if(a.tag && b.tag) {
            c = sum;
            d = diff;
            if(cmp(a, b) < 0) d.tag = false;
        }
        else if(a.tag && !b.tag) {
            c = diff;
            if(cmp(a, b) < 0) c.tag = false;
            d = sum;
            eTag = false;
        }
        else if(!a.tag && b.tag) {
            c = diff;
            if(cmp(b, a) < 0) c.tag = false;
            d = sum;
            d.tag = false;
            eTag = false;
        }
        else {
            c = sum;
            c.tag =false;
            d = diff;
            if(cmp(b, a) < 0) d.tag = false;
        }
        e = MUL(a, b);
        e.tag = eTag;
        print(c); print(d); print(e);
    }
    return 0;
}

编辑于 2020-03-21 22:02:10 回复(0)
// 三个数大小顺序
// 最大公约数 最小公倍数
#include <iostream>
#include <string>
#include <vector>
#include <algorithm>
using namespace std;

typedef struct
{
    vector<int> a;
    vector<int> b;
} BigInt;

void reverseNumber(string str, vector<int> &v)
{
    reverse(str.begin(), str.end()); // 翻转字符串
    for (int i = 0; i < str.size(); i++)
    {
        v.push_back(str.at(i) - '0');
    }
}
void clear(BigInt &BI)
{
    BI.a.clear();
    BI.b.clear();
}
void dealDigit(vector<int> &res_num)
{
    for (int i = res_num.size() - 1; i >= 0; i--) // 去掉多余的0
    {
        if (res_num[i] != 0)
            break;
        else
        {
            res_num.pop_back();
        }
    }

    int c = 0;
    for (int i = 0; i < res_num.size(); i++)
    {
        res_num[i] += c;              // 进位加到高位
        c = res_num[i] / 10;          // 获得进位
        res_num[i] = res_num[i] % 10; // 留下个位
    }
    if (c != 0)
        res_num.push_back(c); // c如果不为0 说明最高位也有进位 加到末尾 反转后c就是最高位
}
void calcMultiply(string A, string B, BigInt BI)
{
    reverseNumber(A, BI.a);
    reverseNumber(B, BI.b);
    int asize = BI.a.size();
    int bsize = BI.b.size();
    vector<int> res_num(asize + bsize, 0);
    for (int i = 0; i < asize; i++) // 逐位相乘
    {
        for (int j = 0; j < bsize; j++)
        {
            res_num[i + j] += (BI.a[i]) * (BI.b[j]);
        }
    }

    dealDigit(res_num);
    for (int i = res_num.size() - 1; i >= 0; i--)
    {
        cout << res_num[i];
    }
    cout << endl;
    clear(BI);
}
int saveVisit(vector<int> v, int i)
{
    if (i >= v.size())
        return 0;
    return v[i];
}
void calcAdd(string A, string B, BigInt BI)
{
    reverseNumber(A, BI.a);
    reverseNumber(B, BI.b);
    int asize = BI.a.size();
    int bsize = BI.b.size();
    vector<int> res_num(asize + bsize, 0);

    for (int i = 0; i < max(asize, bsize); i++)
    {
        res_num[i] = saveVisit(BI.a, i) + saveVisit(BI.b, i);
    }
    dealDigit(res_num);
    for (int i = res_num.size() - 1; i >= 0; i--)
    {
        cout << res_num[i];
    }
    cout << endl;
    clear(BI);
}
void calcSub(string A, string B, BigInt BI)
{
    reverseNumber(A, BI.a);
    reverseNumber(B, BI.b);
    int asize = BI.a.size();
    int bsize = BI.b.size();
    //去除大整数的前导0
    while (BI.a[asize - 1] == 0 && asize > 1)
    {
        asize--;
    }

    while (BI.b[bsize - 1] == 0 && bsize > 1)
    {
        bsize--;
    }

    int maxSize = max(asize, bsize);

    vector<int> res_num(maxSize, 0);
    if (asize < bsize)
    {
        cout << "-";
        BI.a.swap(BI.b);
        swap(asize, bsize);
    }
    if (asize == bsize)
    { // 如果长度相等 依次遍历高位 只要a的高位比b的高位大  就是a-b 若发现b的高位大 则是输出- (a-b)
        for (int i = asize - 1; i >= 0; i--)
        {
            if (BI.a[i] == BI.b[i])
                continue;
            else if (BI.a[i] > BI.b[i])
                break;
            else
            {
                cout << "-";
                BI.a.swap(BI.b);
                swap(asize,bsize);

                break;
            }
        }
    }

    // 减法 a-b
    for (int i = 0; i < maxSize; i++)
    {
        if (BI.a[i] < saveVisit(BI.b,i))
        {
            BI.a[i] += 10;
            BI.a[i + 1]--;
        }
        res_num[i]=(BI.a[i] - BI.b[i]);
    }

    while(res_num[maxSize-1]==0 && maxSize>1){
        maxSize--;
    }
    
    
    for (int i = maxSize -1; i >= 0 ; i--)
    {
        cout << res_num[i];
    }
    cout << endl;
    clear(BI);
}
int main()
{
    string A, B;
    while (cin >> A >> B)
    {
        BigInt BI;
        calcAdd(A, B, BI);
        calcSub(A, B, BI);
        calcMultiply(A, B, BI);
        clear(BI);
    }
    return 0;
}
减法有些难度
发表于 2019-09-11 11:31:28 回复(2)
#include <stdio.h>
#
include <string.h>
const int maxn = 410;
char ainput[maxn];
char binput[maxn];
struct bign{
    int p[maxn];
    int len;
    bign(){
        memset(p, 0, sizeof(p));
        len = 0;
    }
};
// 输出bign
void print(bign a){
     for(int i = 0; i < a.len; i++){
         printf("%d", a.p[a.len - i - 1]);
     }
    printf("\n");
}
// string -> bign
bign change(char s[]){    
    bign a;
    int len = strlen(s);    
    a.len = len;
    for(int i = 0; i < len; i++){
        a.p[len - i - 1] = s[i] - '0';
    }
    return a;
}
// a >= b ?
bool max(bign a, bign b){ 
    if(a.len > b.len)
        return true;
    if(a.len < b.len)
       return false; 
    bool isbig = true;
    for(int i = a.len - 1; i >= 0; i--){
        if(a.p[i] > b.p[i]){
            break;
        }
        if(a.p[i] < b.p[i]){
            isbig = false;
            break;
        }
    }
    return isbig;
}
bign addbign(bign a, bign b){
    bign c;
    int carry = 0;
    c.len = 0;
    for(int i = 0; i < a.len || i < b.len; i++){
        int temp = a.p[i] + b.p[i] + carry;
        c.p[c.len++] = temp % 10;
        carry = temp / 10;
    }
    if(carry != 0){
        c.p[c.len++] = carry;
    }
    return c;
}
// 这里必须 a >= b
bign subbign(bign a, bign b){ 
    bign c;
    c.len = 0;
    for(int i = 0; i < a.len || i < b.len; i++){
        if(a.p[i] >= b.p[i]){
            c.p[c.len++] = a.p[i] - b.p[i];
        }else{
            c.p[c.len++] = a.p[i] + 10 - b.p[i];
            a.p[i+1]--;
        }
    }
    c.len = a.len;
    while(c.len > 1 && c.p[c.len - 1] == 0){
       c.len--;
    }
    return c;
}
// 为乘法做铺垫
// 算 a * q * (10 ^ k); q: 在 0 - 9
bign mutipSub(bign a, int q, int k){  
    bign c;
    c.len = k;
    //先乘10的r次方
    for(int i = 0; i < a.len; i++){
        c.p[c.len++] = a.p[i];
    }
    //再乘q
    int carry = 0;
    for(int i = 0; i < c.len; i++){
        int temp = c.p[i] * q + carry;
        c.p[i] = temp % 10;
        carry = temp / 10;
    }
    while(carry != 0){
        c.p[c.len++] = carry % 10;
        carry = carry / 10;
    }
    return c;
}
//a、b 需都是正数; 负数需要判断负号
bign mutibign(bign a, bign b){
    bign c;
    int k = 0;
    for(int i = 0; i < b.len; i++){
        bign temp = mutipSub(a, b.p[i], k++);
        c = addbign(c, temp);
    }    
    return c;
}
int main(){
     scanf("%s %s", ainput, binput);
   
     bign a = change(ainput);
     bign b = change(binput);
    
    // + 
     bign c1 = addbign(a, b);
     print(c1);
    // -
     if(max(a,b)){
       bign c2 = subbign(a, b);
       print(c2);
     }else{
       bign c2 = subbign(b, a);
       printf("-");
       print(c2);
     }  
     // *
     bign c3 = mutibign(a, b);
     print(c3);
    
    return 0;
}

发表于 2020-03-13 21:38:54 回复(0)

python solution, easy to understand:


while True:
    try:
        a,b=int(input()),int(input())
        print(a+b)
        print(a-b)
        print(a*b)
    except:
        break
发表于 2017-10-01 17:29:27 回复(5)
//说实话代码量有点多...
#include <iostream>
using namespace std;
#include <vector>
#include<string>

class BigNum {
	int a[1000];
	const int MAX = 10;
	const int size = 1000;
public:
	BigNum() { fill(a, a + size, 0); }
	BigNum(string s) {
		fill(a, a + size, 0);
		for (int j = 0, i = s.size() - 1;i >= 0;i--, j++) {
			a[j] = s[i] - '0';
		}
	}
	void operator+(BigNum& B) {
		BigNum C;
		int carry = 0;
		for (int i = 0;i<size;i++) {
			C.a[i] = a[i] + B.a[i] + carry;
			carry = C.a[i] / MAX;
			C.a[i] = C.a[i] % MAX;
		}
		C.print();
	}
	void operator-(BigNum& B) {
        int pos = size - 1;
		while (a[pos] == B.a[pos])pos--;
        if(a[pos] < B.a[pos]){
            for (int i = 0,t;i<size;i++){
                t=a[i];
                a[i]=B.a[i];
                B.a[i]=t;
            } 
            cout<<'-';
        }
        
		BigNum C;
		int carry = 0;
		for (int i = 0;i<size;i++) {

			C.a[i] = a[i] - B.a[i] - carry;
			if (C.a[i] < 0) {
				carry = 1;
				C.a[i] = C.a[i] + MAX;
			}

			else {
				carry = 0;
				C.a[i] = C.a[i] % MAX;
			}
		}
		C.print();
	}

	void operator*(BigNum& B) {
		BigNum C;
		for (int i = 0;i<500;i++) {
			int carry = 0;
			for (int j = 0;j<500;j++) {
				C.a[i + j] = a[i] * B.a[j] + C.a[i + j] + carry;
				carry = C.a[i + j] / MAX;
				C.a[i + j] = C.a[i + j] % MAX;
			}
		}
		C.print();
	}

	void print() {
		int i = size - 1;
		while (a[i] == 0)i--;
		for (;i >= 0;i--) {
			cout << a[i];
		}
		cout << endl;
	}

};
int main() {
	string s1, s2;
	while (cin >> s1 >> s2) {
		BigNum a(s1), b(s2);
		a + b;
		a - b;
		a * b;
	}
}

发表于 2017-07-12 23:52:36 回复(1)
import java.util.*;
import java.math.*;
public class Main{
    public static void main(String[] args){
        Scanner cin=new Scanner(System.in);
        while(cin.hasNext()){
            BigInteger a,b,c;
            a=cin.nextBigInteger();
            b=cin.nextBigInteger();
            System.out.println(a.add(b));
            System.out.println(a.subtract(b));
            System.out.println(a.multiply(b));
        }
    }
} 

发表于 2018-09-15 20:00:26 回复(1)
难以想象,这题用python的解法竟然那么简单,总共7行代码
a=input()
b=input()
a=int(a)
b=int(b)
print(a+b)
print(a-b)
print(a*b)
发表于 2022-03-01 23:11:42 回复(0)
这题真的是入门吗?
发表于 2023-03-18 17:14:52 回复(0)
虽然我用的是cpp,但这种题忍不住不用Python啊!
a = int(input())
b = int(input())
print(a+b)
print(a-b)
print(a*b)


发表于 2023-03-08 14:39:33 回复(0)
写了两天,给👴干吐了,这题入门?确定?还是我太菜了??感觉快抵得上一个课设了吧,,,,
import java.util.Scanner;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        String a = sc.nextLine();
        String b = sc.nextLine();

        if (a.charAt(0) != '-' && b.charAt(0) != '-') {//a b均为正
            String addResult = addfun(a, b);
            System.out.println(addResult);
            String subResult = subfun(a, b);
            System.out.println(subResult);
            String mulResult = mulfun(a, b);
            System.out.println(mulResult);
        }
        if (a.charAt(0) == '-' && b.charAt(0) != '-') {//a负 b正
            String a1 = a.substring(1);
            String addResult = subfun(b, a1);
            System.out.println(addResult);
            String subResult = addfun(a1, b);
            System.out.println("-" + subResult);
            String mulResult = mulfun(a1, b);
            System.out.println("-" + mulResult);
        }
        if (a.charAt(0) != '-' && b.charAt(0) == '-') {//a正 b负
            String b1 = b.substring(1);
            String addResult = subfun(a, b1);
            System.out.println(addResult);
            String subResult = addfun(a, b1);
            System.out.println(subResult);
            String mulResult = mulfun(a, b1);
            System.out.println("-" + mulResult);
        }
        if (a.charAt(0) == '-' && b.charAt(0) == '-') {//a负 b负
            String a1 = a.substring(1);
            String b1 = b.substring(1);
            String addResult = addfun(a1, b1);
            System.out.println("-" + addResult);
            String subResult = subfun(b1, a1);
            System.out.println(subResult);
            String mulResult = mulfun(a1, b1);
            System.out.println(mulResult);
        }
    }

    //两个正数相加
    public static String addfun(String a, String b) {
        //加法
        StringBuilder result = new StringBuilder();
        int i, j;
        int flag = 0;

        for (i = a.length() - 1, j = b.length() - 1; i >= 0 && j >= 0; i--, j--) {
//            char-->String-->int
//            int sum = Integer.parseInt(String.valueOf(a.charAt(i))) + Integer.parseInt(String.valueOf(b.charAt(j)));
            int sum = (a.charAt(i) - '0') + (b.charAt(j) - '0');
            if (flag != 0) {
                sum += 1;     //检查到进了一位,还要加1
                flag = 0;     //刷新
            }
            if (sum > 9) {
                flag = 1;   //此时需要进位,记录一下
                sum = sum - 10; //取个位
            }
            result.append(sum);
        }

        if (i == -1 && j == -1 && flag == 1) result.append('1');//a b一起结束,且有进位
        else {
            if (i != -1) haves(a, result, i, flag);
            if (j != -1) haves(b, result, j, flag);
        }

        String addResult = String.valueOf(result.reverse());

        return addResult;
    }

    //两个正数相减
    private static String subfun(String a, String b) {
        String subResult;
        StringBuilder result = new StringBuilder();
        int i, j;
        int flag = 0;
        int mark = 0;

        if (a.length() < b.length() || (a.length() == b.length() && a.compareTo(b) < 0)) {//使a大 b小
            mark = 1;
            String temp = a;
            a = b;
            b = temp;
        }

        for (i = a.length() - 1, j = b.length() - 1; i >= 0 && j >= 0; i--, j--) {
            int sub;
//            char-->String-->int
            int aint = Integer.parseInt(String.valueOf(a.charAt(i)));
            int bint = Integer.parseInt(String.valueOf(b.charAt(j)));
            if (flag != 0) {
                if (aint > 0) {
                    aint--; //检查到之前借走一位
                    flag = 0;//算过了借的位,刷新
                } else
                    aint = 9;
            }

            if (aint >= bint) {
                sub = aint - bint;
            } else {//需要借一位
                sub = aint + 10 - bint;
                flag = 1;
            }

            result.append(sub);
        }
        while (i >= 0) {
            int aint = Integer.parseInt(String.valueOf(a.charAt(i)));
            if (flag == 1) {

                if (aint > 0) {
                    aint--;
                    flag = 0;
                } else {
                    aint = 9;
                }

                if (aint == 0 && i == 0) break;
                else result.append(aint);

            } else
                result.append(aint);

            i--;
        }

        int k;
        for (k = result.length() - 1; k >= 0; k--) {//从后往前找到最后一个0字符的索引,此时result还是逆序状态
            char m = result.charAt(k);
            if (m != '0') break;
        }

        String res = result.substring(0, k + 1);//修建掉多余的0
        result = new StringBuilder(res);//修改回StringBudil

        if (mark == 1) {
            result.append("-").reverse();
        } else {
            result.reverse();
        }
        subResult = String.valueOf(result);
        return subResult;

    }

    //两个正数相乘
    private static String mulfun(String a, String b) {//a=12345,b=6789

        String mulResult;
        if (a.length() < 5 && b.length() < 5) {
            int aint, bint;

            if (a.isEmpty()) aint = 0;
            else aint = Integer.parseInt(a);

            if (b.isEmpty()) bint = 0;
            else bint = Integer.parseInt(b);

            int result = aint * bint;
            mulResult = String.valueOf(result);
        } else {
            int n;
            if (a.length() < b.length()) n = a.length() / 2;
            else n = b.length() / 2;//n=2
            String A = a.substring(0, a.length() - n - 1);//12
            String B = a.substring(a.length() - n - 1);//345
            String C = b.substring(0, b.length() - n - 1);//6
            String D = b.substring(b.length() - n - 1);//789

            StringBuilder zero1 = new StringBuilder();
            for (int i = 0; i < (n + 1) * 2; i++) {
                zero1.append('0');
            }//zero1:000000
            StringBuilder zero2 = new StringBuilder();
            for (int i = 0; i < n + 1; i++) {
                zero2.append('0');
            }//zero2:000


            String elem1 = mulfun(A, C).concat(String.valueOf(zero1));
            String elem21 = mulfun(A, D);
            String elem22 = mulfun(B, C);
            String elem2 = addfun(elem21, elem22).concat(String.valueOf(zero2));

            String elem3 = mulfun(B, D);

            mulResult = addfun(addfun(elem1, elem2), elem3);
        }

        return mulResult;
    }

    //处理剩余的
    public static void haves(String s, StringBuilder result, int index, int flag) {
        //s是剩余的那个字符串
        while (index >= 0) {
            if (flag == 1) {
                int t = Integer.parseInt(String.valueOf(s.charAt(index--))) + 1;
                if (t > 9) {
                    t = t - 10;
                } else {
                    flag = 0;
                }
                result.append(String.valueOf(t));
            } else {
                result.append(s.charAt(index--));
            }
        }
        if (index == -1 && flag == 1) result.append('1');
    }

}

提交结果:答案正确 运行时间:41ms 占用内存:11208KB 使用语言:Java 用例通过率:100.00%

发表于 2021-02-02 12:48:15 回复(0)
我以为我的代码已经不可能再啰嗦了,不过看到这里有人比我代码还长我就欣慰了,哈哈
#include <stdio.h>
#include <string.h>
#define N 1000

char str[N];
int a[N], b[N];
int sum[N], difference[N], product[N];//和、差、积

void Zero(int num[N])
{//将数组清零
    for(int i=0; i<N; i++) num[i]=0;
}

int GetNum(int num[N], char str[N])
{//从字符串中取得大数,去掉符号并把低位存在前面
    int len=strlen(str);
    int ret=1;//假设是正数
    int i=0, j=0;
    Zero(num);
    if(str[0]=='-')
    {
        j++;
        ret=-1;
    }
    while(j<len) num[i++]=str[j++]-'0';
    int from=0, to=len-1, tmp;
    if(str[0]=='-') to--;
    while(to>from)
    {//把数字转换为低位在前高位在后
        tmp=num[from];
        num[from]=num[to];
        num[to]=tmp;
        from++;
        to--;
    }
    return ret;//返回值是数的正负,负为-1,否则为1
}

int Cmp(int a[N], int b[N])
{//比较a、b的大小,>返回1,<返回-1,=返回0
    for(int i=N-1; i>=0; i--)
    {
        if(a[i]>b[i]) return 1;
        if(a[i]<b[i]) return -1;
    }
    return 0;
}

void Swap(int a[N], int b[N])
{//交换a、b的值
    int tmp;
    for(int i=0; i<N; i++)
    {
        tmp=a[i];
        a[i]=b[i];
        b[i]=tmp;
    }
}

void Add(int sum[N], int a[N], int b[N])
{//求两个正数之和
    Zero(sum);
    for(int i=0; i<N-1; i++)
    {
        sum[i]+=a[i]+b[i];
        if(sum[i]>=10)
        {
            sum[i+1]+=sum[i]/10;
            sum[i]=sum[i]%10;
        }
    }
}

void Subtract(int difference[N], int a[N], int b[N])
{//求两个正数差的绝对值
    Zero(difference);
    if(Cmp(a, b)==-1) Swap(a, b);
    for(int i=0; i<N; i++)
    {
        difference[i]=a[i]-b[i];
    }
    for(int i=0; i<N-1; i++)//从低到高借位
    {
        while(difference[i]<0)
        {
            difference[i]+=10;
            difference[i+1]--;
        }
    }
}

void Multi(int product[N], int a[N], int b[N])
{//求两个正数的积
    Zero(product);
    if(Cmp(a, b)==-1) Swap(a, b);
    //不知道尽量让b小能不能提高效率?
    int hb=N-1, ha=N-1;
    while(b[hb]==0) hb--;//找到b的最高位
    while(a[ha]==0) ha--;//找到a的最高位
    for(int i=0; i<=hb; i++)
    {
        for(int j=0; j<=ha&&i+j<N; j++)
        {
            product[i+j]+=b[i]*a[j];
        }
    }
    for(int i=0; i<N-1; i++)//处理进位
    {
        if(product[i]>=10)
        {
            product[i+1]+=product[i]/10;
            product[i]=product[i]%10;
        }
    }
}

void Output(int num[N])
{//输出一个数
    int high=N-1;
    while(num[high]==0&&high>0) high--;//找到最高位
    for(int i=high; i>=0; i--)
    {
        printf("%d", num[i]);
    }
    printf("\n");
}

int main()
{
    int ta, tb, t;//a的符号、b的符号、得数的符号
    while(scanf("%s", str)!=EOF)
    {
        ta=GetNum(a, str);
        scanf("%s", str);
        tb=GetNum(b, str);
        if(ta==tb)//同为正或同为负
        {
            Add(sum, a, b);
            if(ta==-1) printf("-");//可能需要输出个负号
            Output(sum);
        }
        else//不同号,那加法实际上就是算减法
        {
            if(ta==1)
            {
                if(Cmp(a, b)==-1) t=-1;
                else t=1;
            }
            else//如果a负b正
            {
                if(Cmp(a, b)==1) t=-1;
                else t=1;
            }
            Subtract(difference, a, b);
            if(t==-1) printf("-");//可能需要输出个负号
            Output(difference);
        }
        //接下来是减法,其实就是a+(-b),基本照抄前面
        tb=-tb;//b取反号
        if(ta==tb)//同为正或同为负
        {
            Add(sum, a, b);
            if(ta==-1) printf("-");//可能需要输出个负号
            Output(sum);
        }
        else//不同号,那加法实际上就是算减法
        {
            if(ta==1)
            {
                if(Cmp(a, b)==-1) t=-1;
                else t=1;
            }
            else//如果a负b正
            {
                if(Cmp(a, b)==1) t=-1;
                else t=1;
            }
            Subtract(difference, a, b);
            if(t==-1) printf("-");//可能需要输出个负号
            Output(difference);
        }
        tb=-tb;//把b的符号变回来
        t=ta*tb;
        if(t==-1) printf("-");//可能需要输出个负号
        Multi(product, a, b);
        Output(product);
    }
    return 0;//大功告成
}

发表于 2018-03-07 16:08:03 回复(0)
《入门》
#include <iostream>
#include <string>
#include <algorithm>
using namespace std;

string add(string a, string b);
string sub(string a, string b);
string mup(string a, string b);

int main() {
	string a = "20000000000000000";
	string b = "4000000000000000";
	cin >> a;
	cin >> b;
	cout << add(a,b) << endl;
	cout << sub(a,b) << endl;
	cout << mup(a,b) << endl;

}

string add(string a, string b) {
	string result = "";
	char plusPosition = '0'; // 进位
	int a_index = a.size()-1;
	int b_index = b.size()-1;
	while(a_index>=0 || b_index>=0 || plusPosition!='0') {
		char ca,cb;
		if(a_index>=0) ca = a[a_index--];
		else ca = '0';
		if(b_index>=0) cb = b[b_index--];
		else cb = '0';
		int currentNum = plusPosition + ca + cb - 3*'0';
		plusPosition = currentNum/10 + '0';
		result += currentNum%10 + '0';
	}
	reverse(result.begin(),result.end());
	return result;
}

string sub(string a, string b) {
	string result = "";
	string temp = "0";
	int isBorrow = 0; // 是否借位
	int isChange = 0; // 是否换位
	int a_index = a.size()-1;
	int b_index = b.size()-1;
	
	if(a_index<b_index ) {
		isChange = 1;
		string temp = a;
		a = b;
		b = temp;
		a_index = a.size()-1;
		b_index = b.size()-1;
	}
	if(a_index==b_index){
		
		for(int i=0; i<a.size() && a[i]<=b[i]; i++){
			if(a[i]<b[i]){
				isChange = 1;
				string temp = a;
				a = b;
				b = temp;
				a_index = a.size()-1;
				b_index = b.size()-1;
				break;
			}
		}
	}
	while(a_index>=0 || b_index>=0) {
		char ca,cb;
		temp = "0";
		if(a_index>=0) ca = a[a_index];
		else ca = '0';
		if(b_index>=0) cb = b[b_index];
		else cb = '0';
		int tempNum = ca - cb - isBorrow;
		isBorrow = tempNum>=0 ? 0 : 1;
		tempNum = tempNum>=0 ? tempNum : tempNum+10;
		temp[0] = tempNum+'0'; 
		result += temp;
		a_index--;
		b_index--;
	}
	while( result[result.size()-1] == '0' ){
		result.erase(result.end()-1);
	}
	if(isChange==1) {
		result += '-';
	}
	reverse(result.begin(),result.end());
//	cout << "result = " << result << endl;
	return result;
}

string mup(string a, string b) {
	string result = "";
	int plusPosition = 0; 	// 进位
	string numZero = "";		// 每算一轮,就多加个0
	int a_index = a.size()-1;
	int b_index = b.size()-1;

	for(int i=a_index; i>=0; i--) {
		string sum = "";
		plusPosition = 0;
		string numZeroInner = "";
		for(int j=b_index; j>=0; j--) {	// a的每一个数,×b中的第i个数
			string tempStr = "0";
			int ia = a[i] - '0';
			int ib = b[j] - '0';
			int currentNum = ia * ib + plusPosition;
			char geWei = currentNum%10+'0';		// 当前乘法过后的个位
			tempStr[0] = geWei;
			// 拼接
			tempStr += numZeroInner;
			numZeroInner += "0";
            sum = add(sum, tempStr);
            plusPosition = currentNum/10;	    // 进位
			
		}
		// 完成上步循环未完成的最后一步,加上最高位
		if(plusPosition!=0){
			char c = plusPosition + '0';
			numZeroInner.push_back(c);
			reverse(numZeroInner.begin(),numZeroInner.end());
			sum = add(sum, numZeroInner);
		} 
		// 最终的求和 
		sum += numZero;
		result = add(result, sum);
		numZero += "0";
	}
	return result;
}


编辑于 2024-03-21 01:32:45 回复(0)
#include<stdio.h>
#include<string>
#include<iostream>
using namespace std;
string add(string str1,string str2){
    if(str1=="0" || str1=="")   return str2;
    else if(str2=="0" || str2=="")  return str1;
    if(str1.size() < str2.size())   str1.insert(0,str2.size()-str1.size(),'0');
    else    str2.insert(0,str1.size()-str2.size(),'0');
    int flag=0;
    string res="";
    for(int i=str1.size()-1;i>=0;i--){
        int tmp=str1[i]-'0'+str2[i]-'0'+flag;
        if(tmp>9){
            flag=1;
            res=char(tmp-10+'0')+res;
        }else{
            flag=0;
            res=char(tmp+'0')+res;
        }
    }
    if(flag==1) res='1'+res;
    return res;
}
string sub(string str1,string str2){
    string res="",strd,strx;
    int pos=0,flag=0;  ///flag==0---> str1>str2
    if(str1.size() < str2.size())   str1.insert(0,str2.size()-str1.size(),'0');
    else    str2.insert(0,str1.size()-str2.size(),'0');

    while(str1[pos]==str2[pos] && pos!=str1.size()) pos++;
    if(str1[pos]>str2[pos]){
        strd=str1;
        strx=str2;
    }else{
        strd=str2;
        strx=str1;
        flag=1;
    }
    int carry=0;  ///记录借位情况
    for(int i=strd.size()-1;i>=0;i--){
        int a=strd[i]-'0';
        int b=strx[i]-'0';
        int tmp=a-b-carry;
        if(tmp<0){
            carry=1;
            res=char(tmp+10+'0')+res;
        }else{
            carry=0;
            res=char(tmp+'0')+res;
        }
    }

    if(res=="0")    return "0";
    int j;
    for(j=0;j<res.size();j++){
        if(res[j]!='0') break;

    }
    if(j==res.size())   return "0";
    else    res=res.substr(j);
    if(flag==1) res='-'+res;
    return res;
}
string  mul(string str1,string str2){
    string res="",cstr,dstr;
    int op1,op2,flag,num;
    if(str1.size()<str2.size()){
        cstr=str2;
        dstr=str1;
    }else{
        cstr=str1;
        dstr=str2;
    }
    for(int i=dstr.size()-1;i>=0;i--){
        string tmps="";    ///记录本轮:字符串*字符的结果
        flag=0;
        op2=dstr[i]-'0';    ///乘数
        if(op2==0)  continue;
        for(int j=cstr.size()-1;j>=0;j--){
            op1=cstr[j]-'0';
            num=op1*op2+flag;
            if(num>9){
                flag=num/10;
                num=num%10;
            }else{
                flag=0;
            }
            tmps=char(num+'0')+tmps;
        }
        if(flag!=0) tmps=char(flag+'0')+tmps;
        int add_zero=dstr.size()-1-i;
        while(add_zero!=0){
            tmps.push_back('0');
            add_zero--;
        }
        res=add(res,tmps);
    }
    return res;
}
int main(){
    string str1,str2;
    getline(cin,str1);
    getline(cin,str2);
    printf("%s\n",(add(str1,str2)).c_str());
    printf("%s\n",(sub(str1,str2)).c_str());
    printf("%s\n",(mul(str1,str2)).c_str());
}
编辑于 2024-03-19 23:42:11 回复(0)
Java类库中内置BigInteger类,可直接用于本题求解;但鉴于一些院校的机试系统不允许使用Java,只允许使用C/C++等语言,为练习起见,这里用C++借助结构体(struct)手动实现功能等价的BigInteger类。
#include <iostream>
#include <istream>
#include <ostream>
#include <string>
using namespace std;

const int MAXN = 800;

struct BigInteger {
    int* digit;     //数组存储数值
    int length;     //数组有效长度(数值部分位数)
    int sign;       //符号位,0表示非负数,1表示负数
    BigInteger();
    BigInteger operator=(string str);
    bool operator<(const BigInteger& b);
    BigInteger operator+(const BigInteger& b);
    BigInteger operator-(BigInteger& b);
    BigInteger operator*(const BigInteger& b);
    friend istream& operator>>(istream& in, BigInteger& x);
    friend ostream& operator<<(ostream& out, const BigInteger& x);
};

istream& operator>>(istream& in, BigInteger& x) {
    string str;
    in >> str;
    x = str;
    return in;
}

ostream& operator<<(ostream& out, const BigInteger& x) {
    if (x.sign == 1) {
        out << "-";
    }
    for (int i = x.length - 1; i >= 0; i--) {
        out << x.digit[i];
    }
    return out;
}

BigInteger::BigInteger() {
    digit = new int[MAXN]();
    sign = 0;
    length = 0;
}

BigInteger BigInteger::operator=(string str) {
    length = str.size();
    for (int i = 0; i < length; i++) {
        digit[i] = str[length - i - 1] - '0';
    }
    return *this;
}

bool BigInteger::operator<(const BigInteger& b) {
    if (length < b.length) {
        return true;
    } else if (b.length < length) {
        return false;
    } else {
        for (int i = length - 1; i >= 0; i--) {
            if (digit[i] == b.digit[i]) {
                continue;
            } else {
                return digit[i] < b.digit[i];
            }
        }
    }
    return false;
}

BigInteger BigInteger::operator+(const BigInteger& b) {
    BigInteger answer;
    int carry = 0;
    for (int i = 0; i < length || i < b.length; i++) {
        int current = digit[i] + b.digit[i] + carry;
        carry = current / 10;
        answer.digit[answer.length++] = current % 10;
    }
    if (carry != 0) {
        answer.digit[answer.length++] = carry;
    }
    return answer;
}

BigInteger BigInteger::operator-(BigInteger& b) {
    BigInteger answer;
    if (*this < b) {
        answer = b - *this;
        answer.sign = 1;
        return answer;
    }
    int carry = 0;
    for (int i = 0; i < length || i < b.length; i++) {
        int current = digit[i] - b.digit[i] - carry;
        current < 0 ? current += 10, carry = 1 : carry = 0;
        answer.digit[answer.length++] = current;
    }
    while (answer.digit[answer.length - 1] == 0 && answer.length > 1) {
        answer.length--;
    }
    return answer;
}

BigInteger BigInteger::operator*(const BigInteger& b) {
    BigInteger answer;
    answer.length = length + b.length;
    for (int i = 0; i < length; i++) {
        for (int j = 0; j < b.length; j++) {
            answer.digit[i + j] += digit[i] * b.digit[j];
        }
    }
    for (int i = 0; i < answer.length; i++) {
        answer.digit[i + 1] += answer.digit[i] / 10;
        answer.digit[i] %= 10;
    }
    answer.length++;
    while (answer.digit[answer.length - 1] == 0 && answer.length > 1) {
        answer.length--;
    }
    return answer;
}

int main() {
    BigInteger a, b;
    while (cin >> a >> b) {
        cout << a + b << endl;
        cout << a - b << endl;
        cout << a * b << endl;
    }
    return 0;
}


编辑于 2024-02-29 22:11:16 回复(0)
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;

string addition(string, string);
string subtraction(string, string);
string multiplication(string, string);
int zeroCount(string&);
bool compare(string, string);

int main() {
    string num1, num2;
    while (cin >> num1 >> num2) {
        cout << addition(num1, num2) << endl;
        cout << subtraction(num1, num2) << endl;
        cout << multiplication(num1, num2) << endl;
    }
}

string addition(string a, string b) {
    bool signA = (a[0] == '-');
    bool signB = (b[0] == '-');
    bool resSign;

    if (signA) a.erase(0, 1);
    if (signB) b.erase(0, 1);

    resSign = compare(a, b) ? signA : signB;
    string num1 = compare(a, b) ? a : b; // 大数
    string num2 = compare(a, b) ? b : a; // 小数
    string result = "";

    if (signA == signB) {
        reverse(num1.begin(), num1.end());
        reverse(num2.begin(), num2.end());

        int i;
        bool carry = false;
        for (i = 0; i < num2.size(); i++) {
            int bit = (num1[i] - '0') + (num2[i] - '0');
            if (carry) {
                bit++;
                carry = false;
            }

            if (bit >= 10) {
                bit -= 10;
                carry = true;
            }
            result.push_back(bit + '0');
        }
        for (; i < num1.size(); i++) {
            int bit = (num1[i] - '0');
            if (carry) {
                bit++;
                carry = false;
            }

            if (bit >= 10) {
                bit -= 10;
                carry = true;
            }
            result.push_back(bit + '0');
        }
        if (carry) result.push_back('1');

        reverse(result.begin(), result.end());
        if (resSign) result.insert(0, "-");
    } else {
        result = subtraction(num1, num2);
        if (resSign) result.insert(0, "-");
    }

    return result;
}

string subtraction(string a, string b) { // a - b
    if (a == b) return "0";
    bool signA = (a[0] == '-');
    bool signB = (b[0] == '-');
    bool resSign;

    if (signA) a.erase(0, 1);
    if (signB) b.erase(0, 1);

    string num1 = compare(a, b) ? a : b; // 大数
    string num2 = compare(a, b) ? b : a; // 小数
    string result = "";

    // num1 >= num2
    if (signA != signB) {
        resSign = signA;
        result = addition(num1, num2);
        if (resSign) result.insert(0, "-");
    } else {
        resSign = compare(a, b) ? signA : !signB;
        reverse(num1.begin(), num1.end());
        reverse(num2.begin(), num2.end());

        int i;
        bool borrow = false;
        for (i = 0; i < num2.size(); i++) {
            int bit = num1[i] - num2[i];
            if (borrow) {
                bit--;
                borrow = false;
            }

            if (bit < 0) {
                bit += 10;
                borrow = true;
            }
            result.push_back(bit + '0');
        }
        for (; i < num1.size(); i++) {
            int bit = num1[i] - '0';
            if (borrow) {
                bit--;
                borrow = false;
            }

            if (bit < 0) {
                bit += 10;
                borrow = true;
            }
            result.push_back(bit + '0');
        }
        reverse(result.begin(), result.end());
        while (result[0] == '0') result.erase(0, 1);

        if (resSign) result.insert(0, "-");
    }
    return result;
}

string multiplication(string a, string b) {
    if(a == "0" || b == "0") return "0";

    bool signA = (a[0] == '-');
    bool signB = (b[0] == '-');
    bool resSign = (signA != signB);

    if(signA) a.erase(0,1);
    if(signB) b.erase(0,1);

    //去除多余0
    int zeros = zeroCount(a) + zeroCount(b);
    string zeroStr(zeros,'0');

    string num1 = compare(a,b) ? a : b; // 大数
    string num2 = compare(a,b) ? b : a; // 小数

    vector<string> numSum1;
    string temp = num1;
    numSum1.push_back("0");
    numSum1.push_back(temp);
    for(int i = 0; i < 8; i++) {
        temp = addition(temp,num1);
        numSum1.push_back(temp);
    }

    string result = "0";
    reverse(num2.begin(),num2.end());
    for(int i = 0; i < num2.size(); i++) {
        int bit = num2[i] - '0';
        string tempZeros(i,'0');
        string temp = numSum1[bit] + tempZeros;
        result = addition(result,temp);
    }

    result.append(zeroStr);
    if(resSign) result.insert(0,"-");

    return result;
}

bool compare(string a, string b) { // if a > b, return true
    bool signA = (a[0] == '-');
    bool signB = (b[0] == '-');
    if (signA != signB) return !signA;

    if (signA) a.erase(0, 1);
    if (signB) b.erase(0, 1);

    if (a.size() > b.size()) return !signA;
    else if (a.size() < b.size()) return signB;

    for (int i = 0; i < a.size(); i++) {
        if (a[i] > b[i]) return !signA;
        else if(a[i] < b[i]) return signB;
    }

    return false; // a=b
}

int zeroCount(string& s) {
    int count = 0;
    while (s.back() == '0') {
        count++;
        s.pop_back();
    }
    return count;
}

编辑于 2024-02-20 19:31:31 回复(0)
只想到了用数***算过程字符串实现的办法,,,规定加减乘三种方法的函数内部默认数据为正数,在 main() 根据不同数据正负情况对进行讨论;减法竟然是用了行数最多的一个,,,
#include<string>
#include<iostream>

using namespace std;

string addit(string a, string b){
    string ret;
    if(a.size()<b.size()){
        string temp(b.size()-a.size(), '0');
        a = temp + a;
    }
    else{
        string temp(a.size()-b.size(), '0');
        b = temp + b;
    }
    int adv=0, cur=0;
    char cur_char;
    for(int i=a.size()-1; i>=0; --i){
        cur = (a[i]-'0') + (b[i]-'0') + adv;
        cur_char = cur%10 + '0';
        ret = cur_char + ret;
        adv = cur/10;
    }
    if(adv>0){
        cur_char = adv%10 + '0';
        ret = cur_char + ret;
    }
    return ret;
}

string subst(string a, string b){
    string ret;
    if(a.size()<b.size()){
        string temp(b.size()-a.size(), '0');
        a = temp + a;
    }
    else{
        string temp(a.size()-b.size(), '0');
        b = temp + b;
    }
    int sig=1;
    for(int i=0; i<a.size(); ++i){
        if(a[i]>b[i]) break;
        else if(a[i]<b[i]){
            sig=-1;
            string temp;
            temp=a; a=b; b=temp;
            break;
        }
    }

    int adv=0, cur=0;
    char cur_char;
    for(int i=a.size()-1; i>=0; --i){
        cur = (a[i]-'0') - (b[i]-'0') + adv;
        if(cur>=0){
            cur_char = cur%10 + '0';
            adv = cur/10;
        }
        else{
            cur_char = (10+cur)%10 + '0';
            adv = -1;
        }
        ret = cur_char + ret;
    }
    int zero_index=0;
    for(int i=0; i<ret.size()-1; ++i){
        if(ret[i]=='0') zero_index++;
        else break;
    }
    ret = ret.substr(zero_index);
    if(sig==-1) ret = '-'+ret;
    return ret;
}

string single_multi(string a, char b){
    string ret;
    int adv=0, cur=0;
    char cur_char;
    for(int i=a.size()-1; i>=0; --i){
        cur = (a[i]-'0')*(b-'0') + adv;
        cur_char = cur%10 + '0';
        adv = cur/10;
        ret = cur_char+ret;
    }
    if(adv>0){
        cur_char = adv%10 + '0';
        ret = cur_char + ret;
    }
    return ret;
}

string multi(string a, string b){
    string ret, cur_zero;
    int adv=0, cur=0;
    string cur_char;
    ret='0';
    for(int i=b.size()-1; i>=0; --i, cur_zero+='0'){
        cur_char = single_multi(a, b[i]);
        ret = addit(cur_char+cur_zero, ret);
    }
    return ret;
}

int main(){
    string a, b;
    cin >> a >> b;
    string ret_add, ret_sub, ret_mul;
    // add
    if(a[0]=='-' && b[0]=='-') ret_add = '-'+addit(a.substr(1), b.substr(1));
    else if(a[0]=='-') ret_add = subst(b, a.substr(1));
    else if(b[0]=='-') ret_add = subst(a, b.substr(1));
    else ret_add = addit(a, b);

    // sub
    if(a[0]=='-' && b[0]=='-') ret_sub = subst(b.substr(1), a.substr(1));
    else if(a[0]=='-') ret_sub = '-'+addit(b, a.substr(1));
    else if(b[0]=='-') ret_sub = addit(a, b.substr(1));
    else ret_sub = subst(a, b);

    // mul
    if(a[0]=='-' && b[0]=='-') ret_mul = multi(b.substr(1), a.substr(1));
    else if(a[0]=='-') ret_mul = '-'+multi(b, a.substr(1));
    else if(b[0]=='-') ret_mul = '-'+multi(a, b.substr(1));
    else ret_mul = multi(a, b);

    cout << ret_add << endl << ret_sub << endl << ret_mul;

    return 0;
}


发表于 2023-03-19 16:31:11 回复(0)
#include <algorithm>
#include <iostream>
#include <string>
using namespace std;

string add(string a,string b){//大数加法
    int temp=0,dig=0,na,nb;
    //temp用来保存进位,dig用来记录目前在哪位(比如个位+个位,此时dig是0),na、nb保存对应位的数字
    string re="";//记录最后结果
    reverse(a.begin(), a.end());
    reverse(b.begin(), b.end());
    while(dig<a.size()||dig<b.size()){
        //遍历到最长的字符串完毕,此时比如:a长度是9,b长度是5,那从6号位开始nb=0而na保留对应数字
        na=0;
        nb=0;
        if(dig<a.size()){
            na=(int)(a[dig]-'0');
        }
        if(dig<b.size()){
            nb=(int)(b[dig]-'0');
        }
        re=to_string((temp+na+nb)%10)+re;
        temp=(temp+na+nb)/10;
        dig++;
    }
    if(temp!=0){
        re=to_string(temp)+re;
    }
    return re;
}

string mul(string a,string b){//大数乘法
    int temp,na,nb,keepM;
    string Sre,Are="0";
    //temp用于保存进位,na、nb用来保存对应位的数字
    //思路是模拟乘法,比如a中的第i位的数字na,na*(整个b)得到一个结果Sre,然后Sre末尾加上i个0,再调用大数相加(add)加到Are上
    reverse(a.begin(),a.end());
    reverse(b.begin(),b.end());
    for(int i=0;i<a.size();i++){
        temp=0;
        Sre="";
        na=(int)(a[i]-'0');
        for(int j=0;j<b.size();j++){
            nb=(int)(b[j]-'0');
            keepM=na*nb+temp;
            Sre=to_string(keepM%10)+Sre;
            temp=keepM/10;
        }
        if(temp!=0){
            Sre=to_string(temp)+Sre;
        }
        for(int j=0;j<i;j++){
            Sre=Sre+"0";
        }
        Are=add(Are,Sre);
    }
    return Are;
}
string sub(string a,string b){//减法
    int temp=0,dig=0,na,nb;
    string re="";//记录最后结果
    reverse(a.begin(), a.end());
    reverse(b.begin(), b.end());
    while(dig<a.size()||dig<b.size()){
        na=0;
        nb=0;
        if(dig<a.size()){
            na=(int)(a[dig]-'0');
        }
        if(dig<b.size()){
            nb=(int)(b[dig]-'0');
        }
        if(temp+na-nb<0){
            re=to_string(temp+na-nb+10)+re;
            temp=-1;
        }
        else{
            re=to_string(temp+na-nb)+re;
            temp=0;
        }
        dig++;
    }
    //去掉结果前面的0,比如00023,要改为23
    int tag;
    for(int i=0;i<re.size();i++){
        if(re[i]-'0'!=0){
            tag=i;
            break;
        }
    }
    re=re.substr(tag,re.size()-tag);
    return re;

}
bool cmp(string a,string b){//减法部分,用于比较哪个数大
    if(a.size()==b.size()){
        for(int i=0;i<a.size();i++){
            if(a[i]!=b[i]){
                return a[i]>b[i];
            }
        }
        return true;
    }
    return a.size()>b.size();
}

int main() {
    string a,b,reAdd,reSub,reMul;
    while(cin>>a>>b){
        reAdd=add(a,b);
        if(cmp(a,b)){
            reSub=sub(a,b);
        }
        else{
            reSub="-"+sub(b,a);
        }
        reMul=mul(a,b);

        cout<<reAdd<<endl;
        cout<<reSub<<endl;
        cout<<reMul<<endl;
    }

    return 0;
}

发表于 2023-03-15 10:25:36 回复(0)
//一个题把大数加法,大数减法,大数乘法全考了给我说这是入门题...
#include "stdio.h"
#include "string"
#include "algorithm"
using namespace std;

string addString(string num1,string num2){
    int length = num1.size()>num2.size()?num1.size():num2.size();//length为最长数字串长度
    while (num1.size() < length)
        num1 = "0" + num1;
    while (num2.size() < length)
        num2 = "0" + num2;
    int carry = 0;
    string num3 = "";int temp;//num3为最终计算出的字符串,temp为中间变量
    for (int i = length-1; i >= 0; --i) {
        temp = num1[i]-'0'+num2[i]-'0'+carry;
        if (temp > 9){
            carry = 1;
            num3 += temp-10+'0';
        } else{
            carry = 0;
            num3 += temp+'0';
        }
    }
    if (carry == 1)//最后还有判断是否有进位
        num3 += "1";
    reverse(num3.begin(),num3.end());
    return num3;
}
/*
 * 大数减法思路:先判断被减数和减数的长度,若为被减数长则结果为正,否则为负。若而这长度相等,
 * 则判断哪个数大,不然最后再处理负号会很麻烦。其他的思想就和加法很像了,有个借位的变量,从低位开始
 */
string subString(string num1,string num2){//num1为被减数,num2为减数
    bool flag;//true为正,false为负
    int length1 = num1.size();
    int length2 = num2.size();
    int length;
    if(length1 > length2){//存储长数字串长度且被减数永远是大数
        flag = true;
        length = length1;
    }
    else if (length1 < length2){
        flag = false;
        length = length2;
        swap(num1,num2);
    }
    else{
        int i;
        for (i = 0; i < length1; ++i) {
            if (num1[i] > num2[i]){//num1大
                flag = true;
                length = length1;
                break;
            } else if (num1[i] < num2[i]){//num2大
                flag = false;
                length = length2;
                swap(num1,num2);
                break;
            }
        }
        if (i == length1)
            return "0";
    }//上述为判断减法结果的正负
    while (num1.size() < length)
        num1 = "0" + num1;
    while (num2.size() < length)
        num2 = "0" + num2;
    int borrow = 0;int temp;string num3;
    for (int i = length-1; i >= 0; --i) {
        temp = (num1[i]-'0')-(num2[i]-'0')-borrow;
        if (temp < 0){
            borrow = 1;
            temp += 10;
            num3 += temp + '0';
        } else{
            borrow = 0;
            num3 += temp + '0';
        }
    }
    int i = num3.size()-1;
    while (num3[i] == '0')//消除前导0
        --i;
    num3 = num3.substr(0,i+1);
    reverse(num3.begin(),num3.end());
    if(flag)
        return num3;
    else
        return "-"+num3;
}

string multiString(string num1,string num2){//
    int num3[810] = {0};
    reverse(num1.begin(),num1.end());
    reverse(num2.begin(),num2.end());//为了方便先颠倒过来
    int length1 = num1.size();
    int length2 = num2.size();
    int temp;
    for (int i = 0; i < length1; ++i) {//num3低字节存储地位,所以num3记得颠倒
        for (int j = 0; j < length2; ++j) {
            temp = (num1[i]-'0')*(num2[j]-'0');
            num3[i+j] += temp;
        }
    }
    for (int i = 0; i < 810; ++i) {
        if (num3[i] > 9){
            temp = (num3[i] - num3[i]%10)/10;
            num3[i] = num3[i]%10;
            num3[i+1] += temp;
        }
    }
    int i = 809;
    while (num3[i] == 0)
        --i;//消除前导0,i+1为长度
    string str = "";
    for (int j = 0; j < i+1; ++j) {
        str += num3[j]+'0';
    }
    reverse(str.begin(),str.end());
    return str;
}

int main(){
    char buf1[410],buf2[410];
    string str1,str2;
    while (scanf("%s",buf1)!=EOF){
        scanf("%s",buf2);
        str1 = buf1;str2 = buf2;
        printf("%s\n", addString(str1,str2).c_str());
        printf("%s\n", subString(str1,str2).c_str());
        printf("%s\n", multiString(str1,str2).c_str());
    }
}
发表于 2023-03-14 15:42:18 回复(0)
import java.util.Scanner;

import java.math.BigInteger;
public class Main {
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        while (in.hasNextBigInteger()) {
            BigInteger a = in.nextBigInteger();
            BigInteger b = in.nextBigInteger();
            System.out.println(a.add(b));
            System.out.println(a.subtract(b));
            System.out.println(a.multiply(b));
        }
    }
}

发表于 2023-03-10 12:16:56 回复(0)
#include <algorithm>
#include <cstring>
#include <iostream>
#include <string>
using namespace std;

string jia(string a,string b){
    int l_a = a.length();
    int l_b = b.length();
    int bu = abs(l_a-l_b);
    string k="";
    for(int i=0;i<bu;i++){
        k.append("0");
    }
    if(l_a<l_b){
        a = k+a;
    }
    else if(l_a>l_b){
        b = k+b;
    }
    reverse(a.begin(),a.end());
    reverse(b.begin(),b.end());
    int n = a.length();
    int res[n+1];
    memset(res, 0, sizeof(res));
    for(int j =0;j<n;j++){
        int temp = a[j]-'0' + b[j]-'0' + res[j];
        if(temp>=10){
            res[j] = temp%10;
            res[j+1]++;
        }
        else{
            res[j] = temp;
        }
    }
    string ans="";
    for(int i = n;i>=0;i--){
        if(res[n]==0&&i==n) continue;
        string q =to_string(res[i]);
        ans.append(q);
    }
    return ans;
}
string jian(string a,string b){
    int flag = 0;
    if(a.length()<b.length()) {
        flag = 1;
        swap(a,b);
    }
    else if(a.length()==b.length() && a<b) {
        swap(a,b);
        flag = 1;
    }
    string k="";
    for(int i=0;i<a.length()-b.length();i++){
        k.append("0");
    }
    b=k+b;
    reverse(a.begin(),a.end());
    reverse(b.begin(),b.end());
    for(int i=0;i<a.length();i++){
        a[i] = a[i]-b[i];
        while(a[i]<0){
            a[i] = a[i] + 10;
            a[i+1] --;
        }
    }
    string ans="";
    if(flag==1) ans.append("-");
    for(int i=a.length()-1;i>=0;i--){
        int o = a[i];
        if(o==0 && i==a.length()-1){
            continue;
        }
        ans.append(to_string(o));
    }
    return ans;
}
string cheng(string a,string b){
    int l_a = a.length();
    int l_b = b.length();
    int ans[l_a+l_b];
    memset(ans,0,sizeof(ans));
    reverse(a.begin(),a.end());
    reverse(b.begin(),b.end());
    for(int i=0;i<l_a;i++){
        for(int j=0;j<l_b;j++){
            ans[i+j] = ans[i+j] + (a[i]-'0')*(b[j]-'0');
        }
    }
    for(int i=0;i<l_a+l_b;i++){
        int o = ans[i]/10;
        int p = ans[i]%10;
        ans[i] = p;
        ans[i+1]+=o;
    }
    string res="";
     for(int i=l_a+l_b-1;i>=0;i--){
        if(ans[i]== 0 && i==l_a+l_b-1){
            continue;
        }
        res.append(to_string(ans[i]));
    }
    return res;
}
int main() {
    string str;
    string a,b;
    int k=0;
    while (cin >> str) { // 注意 while 处理多个 case
        if(k==0){
            a = str;
        }
        if(k==1){
            b = str;
            k=0;
            int len_a = a.length();
            int len_b = b.length();
            if(a[0]!='-'&&b[0]!='-'){
                cout << jia(a,b)<<endl;
                cout << jian(a,b)<<endl;
                cout << cheng(a,b)<<endl;
            }
            if(a[0]=='-'&&b[0]=='-'){
                string t_a = a.substr(1,len_a-1);
                string t_b = b.substr(1,len_b-1);
                cout << "-" << jia(t_a,t_b)<<endl;
                cout << jian(t_b,t_a)<<endl;
                cout << cheng(t_a,t_b)<<endl;
            }
            if(a[0]=='-'&&b[0]!='-'){
                string t_a = a.substr(1,len_a-1);
                cout << jian(b,t_a)<<endl;
                cout << "-" << jia(t_a,b)<<endl;
                cout << "-"<<cheng(t_a,b)<<endl;
            }
            if(a[0]!='-'&&b[0]=='-'){
                string t_b = b.substr(1,len_b-1);
                cout << jian(a,t_b)<<endl;
                cout << jia(a,t_b)<<endl;
                cout << "-" << cheng(a,t_b)<<endl;
            }
        }
        k++;
    }
}

发表于 2023-03-04 16:18:02 回复(0)

问题信息

难度:
40条回答 4561浏览

热门推荐

通过挑战的用户

查看代码