c语言数字与字母的乘法,一道C语言面试题:大整数乘法

题目:输入两个数字字符串,如“1234567890”和“987654321”,返回二者相乘的结果字符串,如本例返回为“1219326311126352690”。

来源:某500强企业面试题目

思路:从尾部到头部,对两个字串的每个数字分别相乘,并放入结果字符串相应的位置。

#include "stdio.h"

#include "stdlib.h"

#include "string.h"

char *BigNumMultiply(const char *n1, const char *n2)

{

// quit if n1 or n2 is invalid

if (!n1 || !n2) {

return NULL;

}

// get length

int Len1 = strlen(n1);

int Len2 = strlen(n2);

int Len = Len1 + Len2;

// allocate result buffer

char *ret = (char *)malloc(Len + 1);

if (!ret) {

return NULL;

}

memset(ret, 0, Len + 1);

// multiply

for (int i = Len1 - 1; i >= 0; --i) {

for (int j = Len2 - 1; j >= 0; --j) {

int k = i + j + 1;

// multiply digit by digit

ret[k] += (n1[i] - '0') * (n2[j] - '0');

// add to upper position

if (ret[k] >= 10){

ret[k - 1] += ret[k] / 10;

ret[k] = ret[k] % 10;

}

}

}

// handle first 0

int d = ret[0] == 0 ? 1 : 0;

for (int i = 0; i < Len - d; ++i) {

ret[i] = ret[i + d] + '0';

}

ret[Len - d] = '\0';

return ret;

}

int main(int argc, char* argv[])

{

char n1[] = "1234567890";

char n2[] = "987654321";

char *ret = BigNumMultiply(n1, n2);

printf("%s * %s = %s\n", n1, n2, ret);

free(ret);

ret = NULL;

getchar();

return 0;

}

如下:

d8580c2e870323e71a93565326ac9aa2.png

从工程化角度考虑,有几点需要注意:

1、输入的字符串是否有效?

上面的代码只判断了是否为空,实际上还有可能输入的字符串并非有效的数字字符串,如“12gh34”,这种也需要返回NULL。

2、前导0的处理

a位数与b位数相乘,结果长度可能为a+b,如9*99=891;也可能a+b-1是如 10*100=1000。

在代码的最后部分,对a+b-1的类型进行了移位处理,压缩掉了前导的0。

从编程角度考虑,有几点需要注意:

1、字符串下标从小到大,是从高位到低位。如n=“123”,最高位n[0]=1,最低位n[2]=3。

2、字符ASCII码与字符的转换,如n[3]=5这是纯数字,而+'0'后有n[3]='5'这就是字符了。

3、数字交叉相乘的进位处理,通过 >=10来判断进位,此处注意不要写成>10;另外注意多次叠加,所以使用 +=

4、malloc()的返回值是(void *),为了让编译器happy,需要强制转为(char *),而且最后需要free来释放它申请的内存。

5、字符'0'和字符串“0”的区别

0b1331709591d260c1c78e86d0c51c18.png

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值