浮点异常(核心转储)错误cs50信用问题

问题描述 投票:0回答:1

我正在使用 cs50,尝试运行时遇到此错误。该程序要求用户提供信用卡号,然后使用 luhns 算法和每张卡的要求(通过 printf)报告它是否是有效的 American Express、MasterCard 或 Visa 卡号。源码如下

#include <stdio.h>
#include <cs50.h>

bool validation(long number) {
    int i = 10;
    int j = 1;
    int totalMultiplied = 0;
    int totalNotMultiplied = 0;

    while (number / i != 0){
        totalMultiplied += ((number / i) % 10) * 2;
        i *= 100;
    }
    while (number / j != 0) {
        totalNotMultiplied += (number / j) % 10;
        j *= 100;
    }

    if ((totalMultiplied + totalNotMultiplied) % 10 == 0) {
        return true;
    }else {
        return false;
    }
}

int main(void) {
    long creditCardNo;
    do {
        creditCardNo = get_long("Enter credit card number: ");
    }
    while (creditCardNo < 0);

    int count = 0;
    long startNumbers = creditCardNo;
    long n = creditCardNo;

    do {
        n /= 10;
        count++;
    }
    while (n != 0);

    while (startNumbers >= 100) {
        startNumbers /= 10;
    }

    if (validation(creditCardNo)) {
        if (count == 15 && ( startNumbers == 34 || startNumbers == 35)) {
            printf("AMEX\n");
        }
        else if (count == 16 && ( startNumbers == 51 || startNumbers == 52 || startNumbers == 53 || startNumbers == 54 || startNumbers == 55)) {
            printf("MASTERCARD\n");
        }
        else if ((count == 13 || count == 14) && ( startNumbers / 10 == 4)) {
            printf("VISA\n");
        }
    }else {
        printf("INVALID\n");
    }


}



我希望程序打印卡的类型(如果卡有效)或无效(如果卡无效)

c cs50
1个回答
0
投票

在利用上面关于对整数变量使用“long long”指定的良好注释来测试您的代码时,以下是代码的初始重构,以在验证函数中传递和使用“long long”变量。

首先,在主函数中,信用卡号被重构为一个“long long”变量。

int main(void)
{
    long long creditCardNo;
    do
    {
        creditCardNo = get_long_long("Enter credit card number: ");
    }

然后,函数也按照同样的方式重构了。

bool validation(long long number)   /* Refactored to handle large credit card values    */
{
    long i = 10;
    long j = 1;
    int totalMultiplied = 0;
    int totalNotMultiplied = 0;

    while (number / i != 0)
    {
        totalMultiplied += ((number / i) % 10) * 2;
        printf("totalMultiplied: %d\n", totalMultiplied);           /* Using printf as a manual debug tool  */
        i *= 100;
    }
    while (number / j != 0)
    {
        totalNotMultiplied += (number / j) % 10;
        printf("totalNotMultiplied: %d\n", totalNotMultiplied);     /* Using printf as a manual debug tool  */
        j *= 100;
    }

    if ((totalMultiplied + totalNotMultiplied) % 10 == 0)
    {
        return true;
    }
    else
    {
        return false;
    }
}

虽然这确实解决了溢出问题,但仍然需要在函数中执行一些校验位计算的细化,因为使用“技术上有效”的美国运通信用卡号测试程序时返回无效。

craig@Vera:~/C_Programs/Console/ValidCC/bin/Release$ ./ValidCC 
Enter credit card number: 350000000000006
totalMultiplied: 0
totalMultiplied: 0
totalMultiplied: 0
totalMultiplied: 0
totalMultiplied: 0
totalMultiplied: 0
totalMultiplied: 10
totalNotMultiplied: 6
totalNotMultiplied: 6
totalNotMultiplied: 6
totalNotMultiplied: 6
totalNotMultiplied: 6
totalNotMultiplied: 6
totalNotMultiplied: 6
totalNotMultiplied: 9
INVALID

进一步研究 Luhn 校验位算法的工作原理,当计算结果超过“9”时,需要进行调整,如以下链接所述:

“https://en.wikipedia.org/wiki/Luhn_algorithm”

考虑到这一点,进行了另一次重构改进以模仿 Luhn 校验位算法。

bool validation(long long number)       /* Refactored to handle large credit card values    */
{
    long i = 10;
    long j = 1;
    int totalMultiplied = 0;
    int totalNotMultiplied = 0;

    while (number / i != 0)
    {
        if (((number / i % 10) < 5))                            /* Luhn test    */
            totalMultiplied += ((number / i) % 10) * 2;
        else
            totalMultiplied += ((number / i) % 10) * 2 - 9;
        printf("totalMultiplied: %d\n", totalMultiplied);       /* Using printf as a manual debug tool  */
        i *= 100;
    }
    while (number / j != 0)
    {
        totalNotMultiplied += (number / j) % 10;
        printf("totalNotMultiplied: %d\n", totalNotMultiplied); /* Using printf as a manual debug tool  */
        j *= 100;
    }

    if ((totalMultiplied + totalNotMultiplied) % 10 == 0)
    {
        return true;
    }
    else
    {
        return false;
    }
}

以下是使用相同测试信用卡号的终端输出结果。

craig@Vera:~/C_Programs/Console/ValidCC/bin/Release$ ./ValidCC 
Enter credit card number: 350000000000006
totalMultiplied: 0
totalMultiplied: 0
totalMultiplied: 0
totalMultiplied: 0
totalMultiplied: 0
totalMultiplied: 0
totalMultiplied: 1
totalNotMultiplied: 6
totalNotMultiplied: 6
totalNotMultiplied: 6
totalNotMultiplied: 6
totalNotMultiplied: 6
totalNotMultiplied: 6
totalNotMultiplied: 6
totalNotMultiplied: 9
AMEX

这种额外的改进是先发制人的,以避免在测试程序时出现进一步的混乱。

所有这一切的收获是继续深入研究“C”教程,以更好地理解各种变量定义的局限性,并正确熟悉验证过程(例如校验位推导)的使用。

© www.soinside.com 2019 - 2024. All rights reserved.