diff --git a/sitou/src/B026.java b/sitou/src/B026.java new file mode 100644 index 0000000000000000000000000000000000000000..86c166e2ebaa3a90c0bc4e904ec39743834bd356 --- /dev/null +++ b/sitou/src/B026.java @@ -0,0 +1,66 @@ +package src; + +import java.io.InputStream; +import java.io.PrintStream; +import java.util.ArrayList; +import java.util.List; +import java.util.Scanner; + +public class B026 { + + private static final int[] coinsInMachine = new int[4]; + private static int numOfCustomer; + private static final List> customers = new ArrayList<>(); + private PrintStream out; + + public B026(InputStream in, PrintStream out) { + final Scanner scan = new Scanner(in); + + try { + for (int i = 0; i < coinsInMachine.length; i++) { + coinsInMachine[i] = scan.nextInt(); + } + numOfCustomer = scan.nextInt(); + for (int i = 0; i < numOfCustomer; i++) { + List list = new ArrayList<>(); + for (int j = 0; j < 5; j++) { + list.add(scan.nextInt()); + } + customers.add(list); + } + } finally { + scan.close(); + } + this.out = out; + } + + public static void main(String[] args) { + final B026 sut = new B026(System.in, System.out); + sut.execute(); + } + + public void execute() { + final Result result = solveChange(); + output(result, out); + } + + public static Result solveChange() { + final List result = new ArrayList<>(); + VendingMachine vm = new VendingMachine(coinsInMachine); + + for (int n = 0; n < numOfCustomer; n++) { + // 客ひとりひとりの + // 購入しようとした結果を格納 + final Customer c = new Customer(customers.get(n)); + result.add(c.buy(vm)); + } + return new Result(result); + } + + private static void output(final Result result, final PrintStream out) { + for (int i = 0; i < result.getChange().size(); i++) { + out.println(result.getChange().get(i)); + } + } + +} diff --git a/sitou/src/Customer.java b/sitou/src/Customer.java new file mode 100644 index 0000000000000000000000000000000000000000..0faf57b8843b8ee14b5b34ffb3e159508702336b --- /dev/null +++ b/sitou/src/Customer.java @@ -0,0 +1,21 @@ +package src; + +import java.util.List; + +public class Customer { + private final int drinkPrice; + private final int[] coins = new int[4]; + + public Customer(List customer) { + drinkPrice = customer.get(0); + for (int i = 0; i < 4; i++) { + coins[i] = customer.get(i+1); + } + } + + public String buy(final VendingMachine vm) { + //自動販売機に買いたいモノの値段とコインを渡す。 + //おつりの硬貨の枚数またはimpossibleが返る。 + return vm.sell(drinkPrice, coins); + } +} diff --git a/sitou/src/Result.java b/sitou/src/Result.java new file mode 100644 index 0000000000000000000000000000000000000000..4824803bd6392d870e50abb943cd44209af8d125 --- /dev/null +++ b/sitou/src/Result.java @@ -0,0 +1,15 @@ +package src; + +import java.util.List; + +public class Result { + final List change; + + Result(final List change) { + this.change = change; + } + + public List getChange() { + return change; + } +} diff --git a/sitou/src/VendingMachine.java b/sitou/src/VendingMachine.java new file mode 100644 index 0000000000000000000000000000000000000000..27f68f37f97b985963ed1d1801f1058c67ff4a49 --- /dev/null +++ b/sitou/src/VendingMachine.java @@ -0,0 +1,110 @@ +package src; + +public class VendingMachine { + private static final int _500YEN = 0; + private static final int _100YEN = 1; + private static final int _50YEN = 2; + private static final int _10YEN = 3; + private int[] coins = new int[4]; + + public VendingMachine(int[] coins) { + this.coins = coins; + } + + public String sell(final int price, final int[] receivedCoins) { + final int[] coinsOfChange = { + 0, 0, 0, 0 + }; + final int[] first = { + coins[_500YEN], coins[_100YEN], coins[_50YEN], coins[_10YEN] + }; + final int money = 500 * receivedCoins[_500YEN] + 100 * receivedCoins[_100YEN] + 50 + * receivedCoins[_50YEN] + 10 * receivedCoins[_10YEN]; + final int change = money - price; + + if (canChange(change, coinsOfChange)) { + // おつりを排出できるとき硬貨の枚数を出力 + for (int i = 0; i < 4; i++) { + coins[i] += receivedCoins[i]; + } + return coinsOfChange[_500YEN] + + " " + + coinsOfChange[_100YEN] + + " " + + coinsOfChange[_50YEN] + + " " + + coinsOfChange[_10YEN]; + + } else { + // できないときは自販機の硬貨の枚数を計算前に戻す + coins[_500YEN] = first[_500YEN]; + coins[_100YEN] = first[_100YEN]; + coins[_50YEN] = first[_50YEN]; + coins[_10YEN] = first[_10YEN]; + return "impossible"; + } + } + + private boolean canChange(final int change, final int[] coinsOfChange) { + int restOfChange = change; + + // 100円を出したいときに50,10円の組み合わせでは出さない + // 50円を出したいときに10円5枚でも出せる + // 同様に500円でもそのような処理にしたが、今回の問題では必要ないかも + while (restOfChange > 0) { + if (restOfChange - 500 >= 0) { + + if (coins[_500YEN] > 0) { + coinsOfChange[_500YEN]++; + coins[_500YEN]--; + } else if (coins[_100YEN] >= 5) { + coinsOfChange[_100YEN] += 5; + coins[_100YEN] -= 5; + } else { + return false; + } + restOfChange -= 500; + continue; + + } else if (restOfChange - 100 >= 0) { + + if (coins[_100YEN] > 0) { + coinsOfChange[_100YEN]++; + coins[_100YEN]--; + } else { + return false; + } + restOfChange -= 100; + continue; + + } else if (restOfChange - 50 >= 0) { + + if (coins[_50YEN] > 0) { + coinsOfChange[_50YEN]++; + coins[_50YEN]--; + } else if (coins[_10YEN] >= 5) { + coinsOfChange[_10YEN] += 5; + coins[_10YEN] -= 5; + } else { + return false; + } + restOfChange -= 50; + continue; + + } else if (restOfChange - 10 >= 0) { + + if (coins[_10YEN] > 0) { + coinsOfChange[_10YEN]++; + coins[_10YEN]--; + } else { + return false; + } + restOfChange -= 10; + continue; + + } + } + + return true; + } +} diff --git a/sitou/test/B026_Test.java b/sitou/test/B026_Test.java new file mode 100644 index 0000000000000000000000000000000000000000..f711ec2963c2f060f85eff186f6d2edc342da80c --- /dev/null +++ b/sitou/test/B026_Test.java @@ -0,0 +1,100 @@ +package test; + +import static org.hamcrest.Matchers.*; +import static org.junit.Assert.*; +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; +import java.io.InputStream; +import java.io.PrintStream; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; +import org.junit.Test; +import src.B026; +import src.Customer; +import src.VendingMachine; + +public class B026_Test { + + @Test + public void 正しく動くかテスト() { + final InputStream is = new ByteArrayInputStream(("1 4 1 20\n" + + "3\n" + + "130 1 0 0 0\n" + + "150 0 2 0 0\n" + + "100 1 0 0 0").getBytes()); + + final ByteArrayOutputStream baos = new ByteArrayOutputStream(); + final PrintStream ps = new PrintStream(baos); + + final B026 sut = new B026(is, ps); + sut.execute(); + + final String result = baos.toString(); + assertEquals("0 3 1 2" + System.lineSeparator() + + "0 0 0 5" + System.lineSeparator() + + "impossible" + System.lineSeparator(), result); + } + + @Test + public void impossibleの後に購入できるかテスト() { + final int[] coinsInMachine = { + 0, 5, 1, 10 + }; + final int numOfCustomer = 3; + final List> customers = Arrays + .asList(Arrays.asList(130, 1, 0, 0, 0), Arrays.asList(150, 1, 0, 1, 0), Arrays + .asList(170, 0, 2, 0, 0)); + + final List result = new ArrayList<>(); + VendingMachine vm = new VendingMachine(coinsInMachine); + + for (int n = 0; n < numOfCustomer; n++) { + final Customer c = new Customer(customers.get(n)); + result.add(c.buy(vm)); + } + + assertThat(result, is(contains("0 3 1 2", "impossible", "0 0 0 3"))); + } + + @Test + public void おつりが0円のときを含むテスト() { + final int[] coinsInMachine = { + 0, 0, 0, 2 + }; + final int numOfCustomer = 3; + final List> customers = Arrays + .asList(Arrays.asList(110, 0, 1, 0, 1), Arrays.asList(120, 0, 1, 1, 0), Arrays + .asList(150, 0, 1, 1, 0)); + + final List result = new ArrayList<>(); + VendingMachine vm = new VendingMachine(coinsInMachine); + + for (int n = 0; n < numOfCustomer; n++) { + final Customer c = new Customer(customers.get(n)); + result.add(c.buy(vm)); + } + + assertThat(result, is(contains("0 0 0 0", "0 0 0 3", "0 0 0 0"))); + } + + @Test + public void 自動販売機内の硬貨が全て0のときのテスト() { + final int[] coinsInMachine = { + 0, 0, 0, 0 + }; + final int numOfCustomer = 2; + final List> customers = Arrays + .asList(Arrays.asList(110, 0, 2, 0, 0), Arrays.asList(170, 1, 0, 0, 0)); + + final List result = new ArrayList<>(); + VendingMachine vm = new VendingMachine(coinsInMachine); + + for (int n = 0; n < numOfCustomer; n++) { + final Customer c = new Customer(customers.get(n)); + result.add(c.buy(vm)); + } + + assertThat(result, is(contains("impossible", "impossible"))); + } +}