HiveBrain v1.2.0
Get Started
← Back to all entries
patternjavaMinor

Cash Register Challenge

Submitted by: @import:stackexchange-codereview··
0
Viewed 0 times
challengeregistercash

Problem

Challenge: Design a cash register program

Specifications: Your register currently has the following bills/coins within it:


'PENNY': .01,


'NICKEL': .05,


'DIME': .10,


'QUARTER': .25,


'HALF DOLLAR': .50,


'ONE': 1.00,


'TWO': 2.00,


'FIVE': 5.00,


'TEN': 10.00,


'TWENTY': 20.00,


'FIFTY': 50.00,


'ONE HUNDRED': 100.00


Your program should accept as its first argument a path to a filename.
The input file contains several lines. Each line is one test case.
Each line contains two numbers which are separated by a semicolon.
The first is the Purchase price (PP) and the second is the cash(CH).


For each set of input produce a single line of output,
which is the cashBack to be returned to the customer.
In case the CH < PP, print out ERROR. If CH == PP, print out ZERO.
For all other cases print the amount that needs to be returned,
in terms of the currency values provided.
The output should be sorted in highest-to-lowest order

Solution:

```
import java.io.File;
import java.io.FileNotFoundException;
import java.util.Scanner;

public class CashRegister {
public static void main(String[] args) throws FileNotFoundException {
File file = new File(args[0]);
Scanner fileInput = new Scanner(file);

while (fileInput.hasNextLine()) {
printCashChange(fileInput.nextLine());
}
}

private static void printCashChange(String line) {
float pp = Float.parseFloat(line.split(";")[0]);
float ch = Float.parseFloat(line.split(";")[1]);

System.out.println(getCashChange(pp, ch));
}

private static String getCashChange(float price, float cash) {
if (cash 0.01f) {
if (cashBack >= 100.0f) {
change.append("ONE HUNDRED");
cashBack -= 100.0f;
} else if (cashBack >= 50.0f) {
change.append("FIFTY");
cashBack -= 50.0f;
} else

Solution

For convenience, even though the challenge doesn't specify it, I suggest optionally taking input from System.in. It's more reasonable behaviour than crashing with an ArrayIndexOutOfBoundsException.

Scanner input = (args.length > 0) ? new Scanner(new File(args[0]))
                                  : new Scanner(System.in);


In printCashChange(), avoid two calls to split().

String[] fields = line.split(";", 2);
float pp = Float.parseFloat(fields[0]);
float ch = Float.parseFloat(fields[1]);


The loop in getCashChange() should be data-driven, like this:

for (Denomination d : Denomination.values()) {
    while (cashBack >= d.getValue()) {
        cashBack -= d.getValue();
        change.append(d).append(',');
    }
}


Here's an enum to support that:

public enum Denomination {
    ONE_HUNDRED(100.00f),
          FIFTY( 50.00f),
         TWENTY( 20.00f),
            TEN( 10.00f),
           FIVE(  5.00f),
            TWO(  2.00f),
            ONE(  1.00f),
    HALF_DOLLAR(  0.50f),
        QUARTER(  0.25f),
           DIME(  0.10f),
         NICKEL(  0.05f),
          PENNY(  0.01f);

    private final float value;
    private final String description;

    Denomination(float value) {
        this.value = value;
        this.description = this.name().replace("_", " ");
    }

    public float getValue() {
        return this.value;
    }

    @Override
    public String toString() {
        return this.description;
    }
}


The performance of your program will be fine. You aren't doing anything particularly inefficient, and the bottleneck will be I/O rather than processing.

Code Snippets

Scanner input = (args.length > 0) ? new Scanner(new File(args[0]))
                                  : new Scanner(System.in);
String[] fields = line.split(";", 2);
float pp = Float.parseFloat(fields[0]);
float ch = Float.parseFloat(fields[1]);
for (Denomination d : Denomination.values()) {
    while (cashBack >= d.getValue()) {
        cashBack -= d.getValue();
        change.append(d).append(',');
    }
}
public enum Denomination {
    ONE_HUNDRED(100.00f),
          FIFTY( 50.00f),
         TWENTY( 20.00f),
            TEN( 10.00f),
           FIVE(  5.00f),
            TWO(  2.00f),
            ONE(  1.00f),
    HALF_DOLLAR(  0.50f),
        QUARTER(  0.25f),
           DIME(  0.10f),
         NICKEL(  0.05f),
          PENNY(  0.01f);

    private final float value;
    private final String description;

    Denomination(float value) {
        this.value = value;
        this.description = this.name().replace("_", " ");
    }

    public float getValue() {
        return this.value;
    }

    @Override
    public String toString() {
        return this.description;
    }
}

Context

StackExchange Code Review Q#78071, answer score: 9

Revisions (0)

No revisions yet.