【问题标题】:Multiplying two long long ints C将两个 long long int C 相乘
【发布时间】:2009-12-06 19:09:34
【问题描述】:

我正在使用 C 语言编写一个程序,作为作业的一部分,我必须得到两个长数字的乘积,它们被视为字符串。例如:123456789021 和 132456789098。由于它被视为字符串,因此我将它们转换为 long long int 以进行乘法运算。但是生成的产品会非常大(我猜比 long long int 大)。谁能给我建议一种方法来执行这个乘法?

【问题讨论】:

    标签: c int long-integer multiplication


    【解决方案1】:

    这是一种方法:考虑如何在纸上手工将这些数字相乘。在 C 中实现此方法。您将不得不发现:

    • 如何将整数(表示为字符串)分解为数字
    • 如何将每个数字转换回整数0 <= d < 10
    • 如何管理数字数组(即,您应该使数组有多大?)
    • 如何编写实现乘法可能需要的循环
    • 如何管理将产品从一位数转移到下一位
    • 如何将这些数字转换回字符以供输出

    【讨论】:

    • 如果不是因为您的输入和输出都以 10 为底,您可以通过使用以 2^32 为底(以 64 位类型保存的数字)或基数 2^16(32 位类型)而不是基数 10。
    【解决方案2】:

    通常表示为字节数组的大整数。您可以查看 Microsoft 在 DLR 中的 BigInteger 实现。我认为他们使用了 Knuth 开发的算法

    【讨论】:

      【解决方案3】:

      请查看此 BigInteger library 和来自 World of Seven 的 very basic sample code

      如果你对我用 C 语言编写的一些自制代码感兴趣(仅乘法):

      ////////////////////////////////////////////////////////////////////////////////
      
      Code removed after I checked the home-work tag ;)
      
      ///////////////////////////////////////////////////////////////////////////////////////
      

      这在我参加过的一些早期编程竞赛中有效;)但是如果您正在寻找更快的乘法算法,您可以实现Karatsuba algorithm,我个人现在在实时竞赛中使用它。

      【讨论】:

      • (第一个链接到 Mahbub Murshed SumanBigInteger 类(版本 6.7.28,2004 年 7 月 30 日),第二个来自 World of Seven - Competitive Programming,即使 URL 显示为“steven”。)
      【解决方案4】:

      嘿伙计,看看这个,我昨天刚刚完成了它作为我家庭作业的一部分:

      #include<stdio.h>
      #include<string.h>
      
      int main()
      {
          char one[195];
          char two[195];
          char temp[195];
          int a[195],c[195],b[195];
          int x,i,j,k,l,p,add;
      
          for(;;)/*determining the larger number...*/
          {
              printf("Input A:");
                  gets(one);
              printf("Input B:");
                  gets(two);
      
              k=strlen(one);
              l=strlen(two);
              if(l>k)
              {
                  strcpy(temp,one);
                  strcpy(one,two);
                  strcpy(two,temp);
                  break;
              }
              else
              {
                  break;
              }
          }
              k=strlen(one);
              l=strlen(two);
          for(p=0;p<195;p++)/*assigning all initial values to 0*/
          {
              a[p]=0;
              b[p]=0;
              c[p]=0;
          }
      
          for(i=0;one[i];i++)/*converting char to integer(note:1,as a character assigned as 49.)*/
          {
              a[i]=((one[--k])-48);
          }
      
          for(i=0;i<two[i];i++)
          {
              b[i]=((two[--l])-48);
          }
      
      
          for(i=0;i<=strlen(two);i++)/*main algorithm*/
          {
              add=0;
              p=0;
              for(j=i;j<=(2*strlen(one)-1);j++)
              {
                  x=c[j]+b[i]*a[p]+add;
                  c[j]=x%10;
                  add=x/10;
                  p++;
              }
          }
      
          printf("\nMultiplication:");
          for(p=(2*strlen(one)-1);p>=0;p--)
          {
              if(p>strlen(one)&&c[p]==0)
              {
                  continue;
              }
              printf("%d",c[p]);
          }
          printf("\n");
      }
      

      【讨论】:

        【解决方案5】:

        您可以使用一个库进行大整数运算,维基百科有一个列表here

        【讨论】:

        • 虽然大量库通常很有帮助,但我相信这会违背问题背后的思想和目的。
        【解决方案6】:

        另一种方法是将数字乘以浮点数/双精度数,并在显示结果时去掉小数。

        【讨论】:

        • 这样做可能会损失很多精度。
        • 如果数字太多,那将无法给出确切的答案。根据用例,它可能已经足够好了,但我认为这不是任务的重点。
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-05-08
        • 1970-01-01
        • 2020-04-11
        • 1970-01-01
        • 1970-01-01
        • 2016-07-29
        相关资源
        最近更新 更多