以编程方式求解模数方程

时间:2014-12-04 11:13:13

标签: c# algorithm modulo

我的目标是按照Here

所述实现一个(简单的)校验位数字算法

我的实现如下,但我不确定它是否是最佳的:

 private int CheckDigit(string SevenDecimal)
        {
            ///Get UPC check digit of a 7-digit URI
            ///Add odd and multiply by 3 =Odds
            ///Add even =Evens
            ///Add Odds+Evens=sum
            ///Check digit is the number that makes Sum divisble by 10
            int Odds = 0;
            int Evens = 0;
            int sum = 0;
            int index = 0;
            foreach (char digit in SevenDecimal)
            {
                index++;
                int Digit = int.Parse(digit.ToString());

                if (index % 2 == 0)
                {
                    Evens +=Digit;
                }
                else
                {
                    Odds +=Digit;
                }
            }
            Odds = Odds * 3;
            sum = Odds + Evens;


            for (int i = 0; i < 10; i++)  ///Brute force way check for better implementation
            {
                int Localsum;
                Localsum = sum + i;
                if (Localsum % 10 == 0)
                {
                    return i;
                }
            }
           return -1;//error;                
        }

我主要担心的是最终的for循环,正如我所描述的那样完全是粗野的。 有没有更好的方法来获得校验位?

更准确地说,这是以编程方式解决的最佳方法,方程式:

(sum+x)%10=0  //solve for x

2 个答案:

答案 0 :(得分:1)

要查找“您需要添加多少i才能使数字的最后一位数为0”,您可以从10减去

int checkDigit = (10 - (sum % 10)) % 10;

第二个模数用于sum % 10 == 0时的特殊情况,因为10 - 0 = 10

答案 1 :(得分:0)

你问的是错误的问题。表达式不是等价的,因此x不是。解决方案是x是无穷多个值,每个值都能正确地求解方程。因此,您并不想solve for x,只需检查此解决方案空间中是否x。您可以通过以下方式检查:

remainder = base - (sum % base)

然后,您可以测试x是否与剩余部分相加:

if (x % base === base - (sum % base))
{
    // (sum + x) % base = 0 is true
}

base替换为10,您就可以拥有它。