CS50中Luhn算法C语言实现问题:所有卡号校验均无效
排查Luhn算法校验全无效的问题
核心问题:变量类型溢出导致计算错误
你将long类型的cardnumber赋值给int类型的workingcc,但信用卡号通常是13-16位,远超出int的取值范围(一般为-231到231-1,最多容纳10位有效数字)。一旦卡号长度超过10位,workingcc会触发整数溢出,存储的数值完全失真,后续Luhn算法的计算逻辑自然全部出错,导致所有卡号都被判定为无效。
次要问题:代码粘贴遗漏(不影响运行但需补全)
你提供的代码中第二个while循环缺少闭合的},不过你提到代码可正常运行,应该是粘贴时的遗漏,这个问题不影响当前的校验失效问题。
修正方案
将workingcc的类型改为long,与cardnumber保持一致,避免溢出:
#include <cs50.h> #include <stdio.h> int main(void) { long firsttwodig; long cardnumber; int sum = 0; int count = 0; cardnumber = get_long("card number:"); firsttwodig = cardnumber; // first case of luhn alg long workingcc = cardnumber; // 改为long类型避免溢出 while(workingcc > 0) { int lastdig = workingcc % 10; sum = sum + lastdig; workingcc = workingcc / 100; count++; // 可在此统计卡号位数,用于后续卡种判断 } // second case of luhn alg workingcc= cardnumber / 10; while(workingcc > 0) { int lastdig = workingcc % 10; int timestwo = lastdig * 2; sum = sum +(timestwo % 10) + (timestwo / 10); workingcc = workingcc / 100; count++; } // 补充Luhn校验的最终判断 if (sum % 10 == 0) { // 此处需补充通过firsttwodig和count判断卡种的逻辑 printf("VALID\n"); } else { printf("INVALID\n"); } return 0; }
另外,你还需要完善firsttwodig的处理逻辑——通过循环去掉末尾数字得到卡号前两位,再结合统计的卡号位数,判断卡片类型(Visa、MasterCard、Amex等),但当前校验全无效的核心问题已通过修正变量类型解决。
内容的提问来源于stack exchange,提问作者Jwan Kamal
相关产品推荐
相关产品推荐

