云曦

Choice is more important than effort

0%

大整数类

大整数模拟四则运算

用结构体模拟大整数(很长很多位的数字)四则运算

数组存储

整数高位存储在数组高位,整数的低位存储在数组的低位
1
2
3
4
5
6
7
8
9
struct bign{
int d[1000];
int len; // 记录长度
bign()
{
memset(d,0,sizeof d);
len = 0;
}
};

输入大整数时,都是字符串读入,再把字符串另存至 bign 结构体,倒序存储

1
2
3
4
5
6
7
8
9
10
bign change(char str[])
{
bign a;
a.len = strlen(str);
for(int i = 0; i < a.len;i++)
{
a.d[i] = str[len-i-1] - '0';
}
return a;
}

比较整数大小

  • 比较长度
  • 如果长度相等,则从高位至低位依次比较,直到出现某一位不等,就可以找出大小。
1
2
3
4
5
6
7
8
9
10
11
12
13
int compare(bign a,bign b)
{
if(a.len > b.len) return 1; // a大
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; // 相等
}
}

大整数四则运算

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
bign add(bign a,bign b)
{
bign c;
int carry = 0; // 进位
for(int i = 0; i < a.len || i < b.len;i++)
{
int tmp = a.d[i] + b.d[i] + carry;
c.d[c.len++] = tmp % 10;
carry = tmp / 10;
}
if(carry != 0) // 最后还剩了进位直接赋给高位
{
c.d[c.len++] = carry;
}
return c;
}

总代码加法

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
// 大整数高精度算法c++写法
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;

struct bign {
int d[1000];
int len;
bign() {
memset(d, 0, sizeof d);
len = 0;
}
};

bign change(string str) {
bign a;
a.len = str.length(); // 数字长度
for (int i = 0; i < a.len; i++) {
a.d[i] = str[a.len - i - 1] - '0';
}
return a;
}

bign add(bign a, bign b) {
bign c;
int carry = 0; // 进位
for (int i = 0; i < a.len || i < b.len; i++) {
int tmp = a.d[i] + b.d[i] + carry;
c.d[c.len++] = tmp % 10;
carry = tmp / 10;
}
if (carry != 0) {
c.d[c.len++] = carry;
}

return c;
}

int main() {
string s1, s2;
cin >> s1 >> s2;
bign a = change(s1);
bign b = change(s2);
bign res = add(a, b);
cout << "结果是" << endl;
for (int i = res.len - 1; i >= 0; i--) {

cout << res.d[i];
}
return 0;
}

高精度减法(大数减去小数)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
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+1] -= 1;
a.d[i] += 10;
}
c.d[c.len++] = a.d[i] - b.d[i];
}
while(c.len - 1 >= 1 && c.d[c.len-1] == 0)
{
c.len--; // 去掉前面的0
}
return c;
}

高精度乘法

​ 1 4 7

x 3 5

​ 2 4 5

1 4 0

3 5

把147看作bign类型,35看作 int 类型

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
bign multi(bign a,int b)
{
bign c;
int carry = 0;
for(int i = 0;i < a.len;i++)
{
int t = a.d[i] * b + carry;
c.d[c.len++] = t % 10; // 个位作为该位结果
carry = t / 10; // 高位部分作为新的进位
}
while(carry != 0) // 乘法可能不止一位进位
{
c.d[c.len++] = carry % 10;
carry /= 10;
}
return c;
}