bank

Bank Card Validator in Java

Posted on Updated on

I have recently experimented with Java programming. I have replicated a Luhn algorithm which is used to check the validity of bank cards. This blog concentrates on explaining the source code of the Luhn algorithm.

How it works?
The algorithm splits a card number into two streams. Think about it as stream A and stream B. Stream B remains untouched and all the numbers are added together. The numbers from stream A are each multiplied by two and if after multiplying, the result is a two digit number we add both digits together. In the program the multiplication process is referred to as ‘adding weight’.

        Example:  2 * 6 = 12  1 + 2 = 3

After the multiplication and addition of two digit numbers we add all resulting numbers together. Sums from stream A and stream B are added together and if the number ends with zero the card is valid, if not card is invalid.

Let’s illustrate which numbers are multiplied and which numbers remain the same with a valid card number example.

Table

The Code
Now let’s look at the source code of my program. The first we are going to analyse the functions that handle maths of the two streams.

Stream B 
The function uses a For Loop to crawl through the integer ArrayList and set the numbers irrelevant to stream B to zero. After that the function adds remaining numbers in the ArrayList together and returns a sum of the added numbers.

// No weight math handler
// Return sum of stream b
public static int noWeightAddition (ArrayList<Integer> noWeightArray){
    int sum = 0;
    for (int i = 0; i < noWeightArray.size(); i += 2){
        noWeightArray.set(i, 0);}
    for (int j : noWeightArray){
        sum = sum + j;}
    return sum;}

Stream A
For Loop is used to crawl through the ArrayList and set irrelevant numbers in the ArrayList to zero. Second For Loop is created to crawl through the remaining numbers in the ArrayList and multiply them by two. The If Statement running as a slave code for the second For Loop, handles integers which are greater than nine and splits two digit integers into two separate integers and add them together. Both algorithms outputs are stored in a temporary integer.

You might be asking how is it possible that an integer is gradually filled up? It is not, the integers outputted by the second For Loop and the If Statement are placed into another ArrayList through the temporary integer. The temporary integers value is rewritten each time the second For Loop processes the next integer from the ArrayList outputted by the first For Loop. The second For Loop runs until the end of initial ArrayList that has been outputted by the first For Loop.

// Weight math handler
// Return sum of stream a
public static int weightAddition (ArrayList<Integer> weightArray){
    int sum = 0;
    int tempInt = 0;
    ArrayList<Integer> tempArray = new ArrayList<Integer>();
    for (int i = 1; i < weightArray.size(); i += 2){
        weightArray.set(i, 0);}
    for (int k = 0; k < weightArray.size(); k++){
        tempInt = weightArray.get(k) * 2;
        if (tempInt > 9){
            int a = tempInt /10;
            int b = tempInt %10;
            tempInt = a + b;}
        tempArray.add(tempInt);}
    for (int j : tempArray){
        sum = sum + j;}
    return sum;}

Adding sums together
Output of both stream A and stream B is passed into simple function which adds both together.

// Add sum a and sum b
public static int addedIntStreams (int noWeightStream, int weightStream) {
    return noWeightStream + weightStream;}

Validity decider
The sum is outputted and passed into another boolean function which returns true or false depending on if the ending number is zero or else.

// Validity decider
public static boolean validityDecider (int sum){
    sum = sum %10;
    if (sum == 0){
        return true;
    }else{
        return false;}}

Global variables
The ArrayLists that have been passed into the first two functions as well as Scanner variable that reads user input, have been declared as global variables outside of the main function.

// Global variables
static Scanner cardNumberInput = new Scanner (System.in);
static ArrayList<Integer> number = new ArrayList <Integer>();
static ArrayList<Integer> number2 = new ArrayList <Integer>();

Main function
The user input is a string which populates multiple integer ArrayLists which are used later in each mentioned functions. This block includes exception handling which looks for wrong input such as letters. If correct input is entered the while loop is broken and the program carries on, if the input is incorrect the program loops back to the start of the program.

// Main
public static void main(String args[]) {
    // Loop if input is incorrect
    int x = 1;
    while (x == 1){
        System.out.print("Enter card number: ");

    // String input to integer conversion
    // Array integer insertion
    // Exception handling
    try {
    String inputToChange = cardNumberInput.nextLine();
    for (String part : inputToChange.split(" ")){
        for (int j = 0; j < inputToChange.length(); j++){
            String tempString = String.valueOf(inputToChange.charAt(j));
                int tempInt = Integer.valueOf(tempString);
                number.add(tempInt);
                number2.add(tempInt);
                // Break out
                x=2;}}}
        catch(Exception e){
            System.out.println("Input numbers only!");}}

At last, the functions are glued together in the main function while the integer ArrayLists are passed into the stream A and stream B functions.

// Validity printout
if (validityDecider(addedIntStreams(weightAddition(number), noWeightAddition(number2))) == true){
    System.out.print("CARD IS VALID!");
}else{
    System.out.print("CARD IS NOT VALID!");}

Source code
You can download the source code with few extra bits such as card type recogniser and better program output using regular expressions, from my dropbox.