鱼C论坛

 找回密码
 立即注册
查看: 1534|回复: 0

[技术交流] 大整数的存储与高精度运算

[复制链接]
发表于 2020-2-1 10:02:19 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
本帖最后由 798236606 于 2020-2-1 11:33 编辑
  1. #include<cstdio>
  2. #include<cstring>

  3. typedef struct BIGN{                                         //定义大整数类型
  4.     int num[1000];                                        //从低位到高位存储大整数
  5.     int len;
  6.     bool is_neg;
  7.    
  8.     BIGN()                                                        //初始化构造函数                                       
  9.     {
  10.         memset(num, 0, sizeof(num));
  11.         len = 0;
  12.         is_neg = false;
  13.     };
  14. }bign;

  15. bign str2bign(char *s)                                        //字符串转大整数
  16. {
  17.     bign a;
  18.    
  19.     a.len = strlen(s);
  20.    
  21.     if (s[0] == '-')
  22.     {
  23.         a.is_neg = true;
  24.         a.len--;
  25.         s++;
  26.     }
  27.    
  28.     for (int i = 0; i < a.len; i++)
  29.         a.num[i] = s[a.len - 1 - i] - '0';
  30.         
  31.     return a;
  32. }

  33. void print_bign(bign a)                                //打印大整数
  34. {
  35.     if (a.is_neg)
  36.         putchar('-');
  37.         
  38.     for (int i = a.len - 1; i >= 0; i--)
  39.         printf("%d", a.num[i]);
  40. }

  41. int u_campare(bign a, bign b)                        //无符号比较大小,a > b则返回1,a < b返回-1,a == b返回0
  42. {   
  43.     if (a.len > b.len)
  44.         return 1;
  45.         
  46.     if (a.len < b.len)
  47.         return -1;
  48.         
  49.     for (int i = a.len - 1; i >= 0; i--)
  50.     {
  51.         if (a.num[i] > b.num[i])
  52.             return 1;
  53.         
  54.         if (a.num[i] < b.num[i])
  55.             return -1;
  56.     }
  57.    
  58.     return 0;
  59. }

  60. int campare(bign a, bign b)                                //有符号比较大小
  61. {

  62.     if (a.is_neg == b.is_neg)
  63.         return a.is_neg ? -u_campare(a, b) : u_campare(a, b);
  64.     else
  65.         return a.is_neg ? -1 : 1;
  66. }

  67. bign u_add(bign a, bign b)                                //无符号加
  68. {
  69.     bign c;
  70.     int carry = 0;
  71.    
  72.     for (int i = 0; i < a.len || i < b.len; i++)
  73.     {
  74.         int temp = a.num[i] + b.num[i] + carry;
  75.         
  76.         c.num[c.len++] = temp % 10;
  77.         carry = temp / 10;
  78.     }
  79.    
  80.     if (carry)
  81.         c.num[c.len++] = carry;

  82.     return c;
  83. }

  84. bign u_sub(bign a, bign b)                                //无符号减
  85. {
  86.     bign c;
  87.    
  88.     if (u_campare(a, b) < 0)
  89.     {
  90.         bign temp = a;
  91.         
  92.         a = b;
  93.         b = temp;
  94.         c.is_neg = true;
  95.     }
  96.    
  97.     for (int i = 0; i < a.len || i < b.len; i++)
  98.     {
  99.         if (a.num[i] < b.num[i])
  100.         {
  101.             a.num[i + 1]--;
  102.             a.num[i] += 10;
  103.         }
  104.         
  105.         c.num[c.len++] = a.num[i] - b.num[i];
  106.     }
  107.    
  108.     while (c.len > 1 && !c.num[c.len - 1])
  109.         c.len--;

  110.     return c;
  111. }

  112. bign muti(bign a, int b)                                //有符号乘(大整数乘整形)
  113. {
  114.     bign c;
  115.     int carry = 0;
  116.    
  117.     if (!b)
  118.     {
  119.         c.len++;
  120.         c.is_neg = a.is_neg;
  121.         
  122.         return c;
  123.     }
  124.    
  125.     if (a.is_neg + (b < 0) == 1)
  126.         c.is_neg = true;
  127.         
  128.     if (b < 0)
  129.         b = -b;
  130.         
  131.     for (int i = 0; i < a.len; i++)
  132.     {
  133.         int temp = a.num[i] * b + carry;
  134.         
  135.         c.num[c.len++] = temp % 10;
  136.         carry = temp / 10;
  137.     }

  138.     while (carry)
  139.     {
  140.         c.num[c.len++] = carry % 10;
  141.         carry /= 10;
  142.     }   

  143.     return c;
  144. }

  145. bign divi(bign a, int b)                                        //有符号除(大整数除整形)
  146. {
  147.     bign c;
  148.     int r = 0;
  149.    
  150.     if (!b)
  151.     {
  152.         puts("0 can not be divisor!!");
  153.         
  154.         return c;
  155.     }
  156.    
  157.     if (a.is_neg + (b < 0) == 1)
  158.         c.is_neg = true;
  159.         
  160.     if (b < 0)
  161.         b = -b;
  162.    
  163.     c.len = a.len;   
  164.     for (int i = a.len - 1; i >= 0; i--)
  165.     {
  166.         r = r * 10 + a.num[i];
  167.         c.num[i] = r / b;
  168.         r = r % b;
  169.     }
  170.    
  171.     while (c.len > 1 && !c.num[c.len - 1])
  172.         c.len--;

  173.     return c;
  174. }

  175. bign add(bign a, bign b)                                //有符号加
  176. {
  177.     bign c;
  178.    
  179.     if (a.is_neg == b.is_neg)
  180.     {
  181.         c = u_add(a, b);
  182.         
  183.         if (a.is_neg)
  184.             c.is_neg = true;        
  185.     }
  186.     else
  187.         c = a.is_neg ? u_sub(b, a) : u_sub(a, b);

  188.     return c;
  189. }

  190. bign sub(bign a, bign b)                                //有符号减
  191. {
  192.     bign c;
  193.    
  194.     if (a.is_neg != b.is_neg)
  195.     {
  196.         c = u_add(a, b);
  197.         
  198.         if (a.is_neg)
  199.             c.is_neg = true;        
  200.     }
  201.     else
  202.         c = a.is_neg ? u_sub(b, a) : u_sub(a, b);

  203.     return c;
  204. }

  205. int main(void)
  206. {
  207.     char s1[100] = "-123";
  208.     char s2[100] = "23";
  209.     bign a = str2bign(s1), b = str2bign(s2);
  210.    
  211.     print_bign(divi(a, 12));
  212.    
  213.     return 0;
  214. }
复制代码


相关题目:

PTA B_1017 A除以B
https://fishc.com.cn/thread-154914-1-1.html

PTA A_1023 Have Fun with Numbers
https://fishc.com.cn/thread-154917-1-1.html

PTA A_1024 Palindromic Number
https://fishc.com.cn/thread-154921-1-1.html



本帖被以下淘专辑推荐:

小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2025-5-10 09:12

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表