4

所以让我首先说我是一个新手,对 C# 的知识知之甚少。

进入主题:我需要制作一个能够加/减非常大整数的程序。最初,使用 BigInt 只是为了发现它是不允许的。应该有一个合乎逻辑的解决方法吗?我有一个想法,它使用“小学方法”,您从右到左添加每个数字。

我创建了一个字符串,将其拆分为 char 数组并从右到左添加每个数字(GetUpperBound-i)。但这似乎不起作用。

我的代码:

string s, s2;
char[] c_arr, c_arr2;
int i, erg;

s = "1234";
s2 = "5678";
c_arr = s.ToCharArray();
c_arr2 = s2.ToCharArray();
for (i = 0; i <= c_arr.GetUpperBound(0); i++)
{
    erg = c_arr[c_arr.GetUpperBound(0)-i]+c_arr2[c_arr2.GetUpperBound(0)-i];
    Console.Write(erg);
}

Console.ReadKey();
4

6 回答 6

5

您的“小学方法”代码有一些问题。您没有考虑进位,您将 ascii 值而不是 0-9 之间的实际值相加,并且您以错误的顺序输出结果。

下面的代码虽然不是很优雅,但确实产生了正确的结果:

var s1 = "12345";
var s2 = "5678";
var carry = false;
var result = String.Empty;

if(s1.Length != s2.Length)
{
    var diff = Math.Abs(s1.Length - s2.Length);

    if(s1.Length < s2.Length)
    {
        s1 = String.Join("", Enumerable.Repeat("0", diff)) + s1;
    }
    else
    {
        s2 = String.Join("", Enumerable.Repeat("0", diff)) + s2;
    }
}


for(int i = s1.Length-1;i >= 0; i--)
{
    var augend = Convert.ToInt32(s1.Substring(i,1));
    var addend = Convert.ToInt32(s2.Substring(i,1));
    var sum = augend + addend;
    sum += (carry ? 1 : 0);
    carry = false;
    if(sum > 9)
    {
        carry = true;
        sum -= 10;
    }

    result = sum.ToString() + result;
}

if(carry)
{
    result = "1" + result;
}

Console.WriteLine(result);
于 2013-09-23T07:17:55.740 回答
2

下面的程序可以用来添加两个大数,我使用了字符串生成器来存储结果。您可以添加最多包含“2,147,483,647”的数字。

Using System;

using System.Text;

using System.Linq;

public class Test

{

public static void Main()

{

    string term1="15245142151235123512352362362352351236";

    string term2="1522135123612646436143613461344";

    StringBuilder sum=new StringBuilder();

    int n1=term1.Length;

    int n2=term2.Length;

    int carry=0;

    int n=(n1>n2)?n1:n2;

    if(n1>n2)

    term2=term2.PadLeft(n1,'0');

    else

    term1=term1.PadLeft(n2,'0');

    for(int i=n-1;i>=0;i--)

    {

        int value=(carry+term1[i]-48+term2[i]-48)%10;

        sum.Append(value);

        carry=(carry+term1[i]-48+term2[i]-48)/10;

    }

    char[] c=sum.ToString().ToCharArray();

    Array.Reverse(c);

    Console.WriteLine(c);

}

}
于 2015-09-24T11:28:07.780 回答
1
string Add(string s1, string s2)
{
    bool carry = false;
    string result = string.Empty;
    if(s1[0] != '-' && s2[0] != '-')
    {
        if (s1.Length < s2.Length)
            s1 = s1.PadLeft(s2.Length, '0');
        if(s2.Length < s1.Length)
            s2 = s2.PadLeft(s1.Length, '0');

        for(int i = s1.Length-1; i >= 0; i--)
        {
            var augend = Convert.ToInt64(s1.Substring(i,1));
            var addend = Convert.ToInt64(s2.Substring(i,1));
            var sum = augend + addend;
            sum += (carry ? 1 : 0);
            carry = false;
            if(sum > 9)
            {
                carry = true;
                sum -= 10;
            }
            result = sum.ToString() + result;
        }
        if(carry)
        {
            result = "1" + result;
        }
    }

    else if(s1[0] == '-' || s2[0] == '-')
    {
        long sum = 0;
        if(s2[0] == '-')
        {
            //Removing negative sign
            char[] MyChar = {'-'};
            string NewString = s2.TrimStart(MyChar);
            s2 = NewString;

            if(s2.Length < s1.Length)
                s2 = s2.PadLeft(s1.Length, '0');

            for (int i = s1.Length - 1; i >= 0; i--)
            {
                var augend = Convert.ToInt64(s1.Substring(i,1));
                var addend = Convert.ToInt64(s2.Substring(i,1));
                if(augend >= addend)
                {
                    sum = augend - addend;
                }
                else 
                {
                    int temp = i - 1;
                    long numberNext = Convert.ToInt64(s1.Substring(temp,1));
                    //if number before is 0
                    while(numberNext == 0)
                    {
                        temp--;
                        numberNext = Convert.ToInt64(s1.Substring(temp,1));
                    }
                    //taking one from the neighbor number
                    int a = int.Parse(s1[temp].ToString());
                    a--;
                    StringBuilder tempString = new StringBuilder(s1);
                    string aString = a.ToString();
                    tempString[temp] = Convert.ToChar(aString);
                    s1 = tempString.ToString(); 
                    while(temp < i)
                    {
                        temp++;
                        StringBuilder copyS1 = new StringBuilder(s1);
                        string nine = "9"; 
                        tempString[temp] = Convert.ToChar(nine);
                        s1 = tempString.ToString();
                    }
                    augend += 10;
                    sum = augend - addend;
                }
                result = sum.ToString() + result;
            }
            //Removing the zero infront of the answer
            char[] zeroChar = {'0'};
            string tempResult = result.TrimStart(zeroChar);
            result = tempResult;
        }
    }

    return result;
}
string Multiply(string s1, string s2)
{
    string result = string.Empty;
    //For multipication
    bool Negative = false;
    if(s1[0] == '-' && s2[0] == '-')
        Negative = false;
    else if(s1[0] == '-' || s2[0] == '-')
        Negative = true;

    char[] minusChar = {'-'};
    string NewString;
    NewString = s2.TrimStart(minusChar);
    s2 = NewString;
    NewString = s1.TrimStart(minusChar);
    s1 = NewString;

    List<string> resultList = new List<string>();
    for(int i = s2.Length - 1; i >= 0; i--)
    {
        string multiplycation = string.Empty;
        for (int j = s1.Length - 1; j >= 0; j--)
        {
            var augend = Convert.ToInt64(s1.Substring(j,1));
            var addend = Convert.ToInt64(s2.Substring(i,1));
            long multiply = augend * addend;
            // print(multiply); 
            multiplycation = multiply.ToString() + multiplycation;
        }
        //Adding zero at the end of the multiplication
        for (int k =  s2.Length - 1 - i; k > 0; k--)
        {
            multiplycation += "0";
        }
        resultList.Add(multiplycation);
    }

    for (int i = 1; i < resultList.Count; i++)
    {
        resultList[0] = Add(resultList[0],resultList[i]);
    }

    //Finally assigning if negative negative sign in front of the number
    if(Negative)
        result = resultList[0].Insert(0,"-");
    else
        result = resultList[0];

    return result;
}
string Divide(string dividend, string divisor)
{
    string result = string.Empty;

    int remainder = 0;
    int intNumberstoGet = divisor.Length;
    int currentInt = 0;
    int dividing = int.Parse(dividend.Substring(currentInt,intNumberstoGet));

    int intDivisor = int.Parse(divisor);

    while(currentInt < dividend.Length)
    {
        if(dividing == 0)
        {
            currentInt++;
            result += "0";
        }
        else
        {
            while(dividing < intDivisor)
            {
                intNumberstoGet++;
                dividing = int.Parse(dividend.Substring(currentInt,intNumberstoGet));
            }

            if (dividing > 0)
            {   
                remainder = dividing % intDivisor;
                result += ((dividing - remainder) / intDivisor).ToString();
                intNumberstoGet = 1;

                if(currentInt < dividend.Length - 2)
                    currentInt += 2;
                else
                    currentInt++;

                if(currentInt != dividend.Length)
                {
                    dividing = int.Parse(dividend.Substring(currentInt,intNumberstoGet));
                    remainder *= 10;
                    dividing += remainder;
                }
            }
        }
    }
    return result;
}
于 2018-05-20T16:25:59.757 回答
1

干得好。另一个例子。它比公认的答案快 10 到 30 倍。

    static string AddNumStr(string v1, string v2)
    {
        var v1Len = v1.Length;
        var v2Len = v2.Length;
        var count = Math.Max(v1Len, v2Len);
        var answ = new char[count + 1];
        while (count >= 0) answ[count--] = (char)((v1Len > 0 ? v1[--v1Len] & 0xF:0) + (v2Len>0 ? v2[--v2Len]&0xF : 0));
        for (var i = answ.Length - 1; i >= 0; i--)
        {
            if (answ[i] > 9)
            {
                answ[i - 1]++;
                answ[i] -= (char)10;
            }
            answ[i] = (char)(answ[i] | 48);
        }
        return new string(answ).TrimStart('0');
    }
于 2018-08-03T09:22:15.373 回答
0

下面的问题有一些有趣的方法。虽然答案是在 Java 中,但您肯定会知道需要做什么。

如何在不使用 java.math.BigInteger 的情况下在 Java 中处理非常大的数字

于 2013-09-22T17:48:50.177 回答
0
    public static int[] addTwoNumbers(string s1, string s2)
    {

        char[] num1 = s1.ToCharArray();
        char[] num2 = s2.ToCharArray();
        int sum = 0;
        int carry = 0;
        int size = (s1.Length > s2.Length) ? s1.Length + 1 : s2.Length + 1;
        int[] result = new int[size];
        int index = size - 1;
        int num1index = num1.Length - 1;
        int num2index = num2.Length - 1;


        while (true)
        {
            if (num1index >= 0 && num2index >= 0)
            {
                sum = (num1[num1index]-'0') + (num2[num2index]-'0') + carry;
            }
            else if(num1index< 0 && num2index >= 0)
            {
                sum = (num2[num2index]-'0') + carry;
            }
            else if (num1index >= 0 && num2index < 0)
            {
                sum = (num1[num1index]-'0') + carry;
            }
            else { break; }


            carry = sum /10;
            result[index] = sum % 10;
            index--;
            num1index--;
            num2index--;
        } 

            if(carry>0)
            {
                result[index] = carry;
            }


        return result;
    }
于 2017-07-07T03:27:19.827 回答