Java: Как проверить действительность кредитных карт с помощью проверки Luhn и с помощью методов - PullRequest
0 голосов
/ 02 ноября 2019

Я пытался выяснить этот метод Luhns для проверки кредитной карты, но я не могу понять это. Мне нужно использовать методы, и я не могу использовать массивы, так что я полностью в тупике

Вот проверка Luhns:

Номер кредитной карты должен содержать от 13 до 16 цифр. Оно должно начинаться с: ■ 4 для карт Visa ■ 5 для карт Master ■ 37 для карт American Express ■ 6 для карт Discover

  1. Удваивайте каждую секунду цифру справа налево. Если в результате удвоения цифры получается двузначное число, сложите две цифры, чтобы получить однозначное число.
  2. Теперь добавьте все однозначные числа из шага a.
  3. Добавитьвсе цифры в нечетных местах справа налево в номере карты.
  4. Суммируйте результаты шага b и шага c.
  5. Если результат шага d делится на 10, картаномер действителен;в противном случае это недействительно. Например, номер 4388576018402626 недействителен, но номер 4388576018410707 действителен.

Моя проблема в том, что я все еще изучаю методы (Всего новичков. Я пытался научиться кодировать один раз в прошлом году и далвверх, но мне удалось зайти так далеко на этот раз) и я не могу понять, как использовать эти методы для выполнения шагов 4 и 5 из проверки Луна.

Может кто-нибудь попытаться помочьменя нет? Спасибо !!

public static boolean isValid(String x) {
    return false; // Stub method    
}

public static void AddResults() {

}

public static void OddDigits(String s) {
    int sum = 0;
    for (int index = 0; index < s.length(); index ++) {
        if (index % 2 != 0) {
            sum = sum + Character.getNumericValue(s.charAt(index));
        }
    }
    return;
}

public static int DoubleToSingle(int x) { // Adds up the digits in a two-digit number. 
    if (x < 10) {
        return x;
    } 
    else {
        int firstDigit = x % 10;
        int secondDigit = (int)(x / 10);
        return firstDigit + secondDigit;
    }
}

public static void Doubling(String s) {
    int sum = 0;
    for (int index = s.length() - 1; index > 0; index-= 2) {
        int parse = Character.getNumericValue(s.charAt(index));
        if (parse > 9) {
        sum = sum + DoubleToSingle(parse);
        }
        else {
            sum = sum + parse;
        }
    }

    return;
}

public static boolean CheckLength(String s) {
    if (s.length() < 13 || s.length() > 16) { // If the cc number is smaller than 13 digits or larger than 16 digits, it's invalid
        return false;
    }
    else {
        return true;
    }
}

public static String ReadString(Scanner s) { // Creating a string method. (Using it to practice creating methods)
    String x = s.nextLine();
    return x;
}

public static void main(String[] args) {
    Scanner input = new Scanner(System.in);
    System.out.println("Please input a valid Credit Card number: ");
    String CC = ReadString(input);

    if (isValid(CC) == true) {
        System.out.println(CC + " is valid.");
    } else {
        System.out.println(CC + " is invalid.");
    }       
    input.close();
}

1 Ответ

0 голосов
/ 02 ноября 2019

Комментарии к вашему коду:

  • Соглашение об именах Java для имен методов должно начинаться со строчной буквы, как ваш isValid метод.

  • В методе doubleToSingle x - это int, а 10 - это int литерал, поэтому x / 10 будет int, а результат будет усечен, что означает, что нетнеобходимо для этого приведения: (int)(x / 10)

  • Поскольку метод doubleToSingle может обрабатывать однозначные числа, нет необходимости в том, чтобы вызывающий (метод doubling) обрабатывал его,поэтому исключите тест if (parse > 9).

  • Подсчет цифр справа работает следующим образом:

     5th digit       Odd places:
     ↓ 3rd digit       Don't double these digits, just sum them
     ↓ ↓ 1st digit
     ↓ ↓ ↓
    999999
    ↑ ↑ ↑
    ↑ ↑ 2nd digit    Even places, aka "every second digit from right":
    ↑ 4th digit        Double these digits, combine digits when
    6th digit          two-digit number, then sum them
    

    Запускается метод doublingпри индексе last , а не за вторым-последним, как следует, и он пропускает индекс first , чего не должно быть. Цикл должен быть:

    for (int index = s.length() - 2; index >= 0; index -= 2)
    
  • Метод doubling должен действительно удвоить число (parse * 2) перед вызовом метода doubleToSingle.

  • Метод oddDigits считает нечетное / четное от влево , когда он должен считаться от вправо .

    Удалите тест if (index % 2 != 0) и используйте цикл, аналогичный используемому в методе doubling:

    for (int index = s.length() - 1; index >= 0; index -= 2)
    
  • Методы doubling и oddDigits должны returnsum, иначе какой смысл?

Если вы думаете, что отсутствие возврата из методов doubling и oddDigits застало вас, поэтому я позволю вампродолжайте работу над остальной частью своего кода.


Хотя следующий код выходит за рамки вашего текущего уровня навыков, я хочу показать его, чтобы у вас было что-то, на что можно рассчитывать, уметь понимать и в конечном итогенапишите код наподобие этого.

public static boolean isValid(String cc) {
    if (! cc.matches("(?=[456]|37)[0-9]{13,16}"))
        return false;
    int sum = 0;
    for (int i = cc.length() - 1, pos = 1; i >= 0; i--, pos++) {
        int digit = cc.charAt(i) - '0';
        sum += (pos % 2 == 1/*odd*/ ? digit : digit < 5 ? digit * 2 : digit * 2 - 9);
    }
    return (sum % 10 == 0);
}

Он проверяет все условия, перечисленные в вопросе, даже часть "Это должно начинаться с", которую вы не запустилибуду еще. На вашем уровне навыка вам, вероятно, следует использовать s.startsWith("xx") вместо регулярного выражения matches(...), используемого здесь.

...