转自:http://blog.csdn.net/archimedes_zht/article/details/2141881
在ACM的题目中经常会遇到大数相加和相乘的问题,在有些公司的面试题中也有暗含要用大数才能解决的问题。比如:输入三个整数,写一个程序判断这个三个整数能否构成一个直角三角形。此题算法很简单,但是却暗含着结果可能溢出的问题。如果不会用大数,此题就无法给出完美的答案。
下面给出大数的乘法和加法算法:
1、加法:
//
assume m is bigger than n.
char
*
add(
char
*
a,
char
*
b,
int
m,
int
n)
{
//
为结果分配内存空间。
char
*
c
=
(
char
*
)malloc((m
+
2
)
*
sizeof
(
char
));
memset(c,
0
, (m
+
2
)
*
sizeof
(
char
));
//
将字符(0 + 0x30 到 9 + 0x30)转换为数字(0到9)进行计算。
for
(
int
i
=
m, j
=
n
–
1
; j
>=
0
;
—
i,
—
j)
c[i]
+=
(b[j]
–
0x30
);
for
(
int
i
=
m, j
=
m
–
1
; j
>=
0
;
—
i,
—
j)
{
c[i]
+=
(a[j]
–
0x30
);
if
(c[i]
>
9
)
{
c[i
–
1
]
+=
1
;
c[i]
-=
10
;
}
}
//
将由纯数字组成的结果转换为字符串,并去除首部可能还存在的零。
c[m + 1] = ‘/0’;
for
(
int
i
=
0
; i
!=
m
+
1
;
++
i)
c[i]
+=
0x30
;
if
(c[
0
]
==
0x30
)
for
(
int
i
=
0
; c[i] != ‘/0’;
++
i)
c[i]
=
c[i
+
1
];
//
返回结果所在内存单元的首地址。
return
c;
}
2、乘法:
//
assume m is bigger than n.
char
*
mult(
char
*
a,
char
*
b,
int
m,
int
n)
{
//
为结果分配内存空间。
char
*
c
=
(
char
*
)malloc((m
+
n
+
1
)
*
sizeof
(
char
));
memset(c,
0
, (m
+
n
+
1
)
*
sizeof
(
char
));
//
将字符(0 + 0x30 到 9 + 0x30)转换为数字(0到9)进行计算。
for
(
int
i
=
m
–
1
, r
=
m
+
n
–
1
; i
>=
0
;
—
i,
—
r)
{
for
(
int
j
=
n
–
1
, k
=
r; j
>=
0
;
—
j,
—
k)
{
c[k]
+=
(a[i]
–
0x30
)
*
(b[j]
–
0x30
);
int
tmp
=
c[k]
/
10
;
if
(tmp
>
1
)
{
c[k
–
1
]
+=
tmp;
c[k]
-=
tmp
*
10
;
}
}
}
//
将由纯数字组成的结果转换为字符串,并去除首部可能还存在的零。
c[m + n] = ‘/0’;
for
(
int
i
=
0
; i
!=
m
+
n;
++
i)
c[i]
+=
0x30
;
if
(c[
0
]
==
0x30
)
for
(
int
i
=
0
; c[i] != ‘/0’;
++
i)
c[i]
=
c[i
+
1
];
//
返回结果所在内存单元的首地址。
return
c;
}