From 6e3addcaf90fba32d5ee9d0d357fe1f60705b203 Mon Sep 17 00:00:00 2001 From: Huniiiiiii Date: Tue, 27 May 2025 01:30:49 +0900 Subject: [PATCH] =?UTF-8?q?7=EC=A3=BC=EC=B0=A8=20=EB=AF=B8=EC=85=98=20?= =?UTF-8?q?=EC=99=84=EB=A3=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/lotto/Application.java | 6 +- .../lotto/controller/lottoController.java | 36 ++++++++++++ src/main/java/lotto/model/Lotto.java | 45 +++++++++++++++ src/main/java/lotto/model/LottoGenerator.java | 22 ++++++++ src/main/java/lotto/model/LottoResult.java | 34 ++++++++++++ src/main/java/lotto/model/PrizeTier.java | 36 ++++++++++++ src/main/java/lotto/view/LottoView.java | 55 +++++++++++++++++++ 7 files changed, 232 insertions(+), 2 deletions(-) create mode 100644 src/main/java/lotto/controller/lottoController.java create mode 100644 src/main/java/lotto/model/Lotto.java create mode 100644 src/main/java/lotto/model/LottoGenerator.java create mode 100644 src/main/java/lotto/model/LottoResult.java create mode 100644 src/main/java/lotto/model/PrizeTier.java create mode 100644 src/main/java/lotto/view/LottoView.java diff --git a/src/main/java/lotto/Application.java b/src/main/java/lotto/Application.java index d190922..eb14af0 100644 --- a/src/main/java/lotto/Application.java +++ b/src/main/java/lotto/Application.java @@ -1,7 +1,9 @@ package lotto; +import lotto.controller.lottoController; public class Application { public static void main(String[] args) { - // TODO: 프로그램 구현 + lottoController controller = new lottoController(); + controller.run(); } -} +} \ No newline at end of file diff --git a/src/main/java/lotto/controller/lottoController.java b/src/main/java/lotto/controller/lottoController.java new file mode 100644 index 0000000..4d1db50 --- /dev/null +++ b/src/main/java/lotto/controller/lottoController.java @@ -0,0 +1,36 @@ +package lotto.controller; + +import lotto.model.*; +import lotto.view.LottoView; + +import java.util.*; + +public class lottoController { + private final LottoView view = new LottoView(); + + public void run() { + try { + int money = view.askMoney(); + List tickets = generateTickets(money / 1000); + view.printTickets(tickets); + + Set winning = view.askWinningNumbers(); + int bonus = view.askBonusNumber(winning); + + LottoResult result = evaluate(tickets, winning, bonus); + view.printResult(result, money); + } catch (IllegalArgumentException e) { + view.printError(e.getMessage()); + } + } + + private List generateTickets(int count) { + return LottoGenerator.generateMultiple(count); + } + + private LottoResult evaluate(List tickets, Set win, int bonus) { + LottoResult result = new LottoResult(); + tickets.forEach(ticket -> result.add(ticket, win, bonus)); + return result; + } +} \ No newline at end of file diff --git a/src/main/java/lotto/model/Lotto.java b/src/main/java/lotto/model/Lotto.java new file mode 100644 index 0000000..affac73 --- /dev/null +++ b/src/main/java/lotto/model/Lotto.java @@ -0,0 +1,45 @@ +package lotto.model; + +import java.util.*; + +public class Lotto { + private static final int SIZE = 6; + private static final int MIN = 1; + private static final int MAX = 45; + private final List numbers; + + public Lotto(List numbers) { + validate(numbers); + this.numbers = sorted(numbers); + } + + private void validate(List numbers) { + if (numbers.size() != SIZE) + throw new IllegalArgumentException("[ERROR] 로또 번호는 6개여야 합니다."); + if (new HashSet<>(numbers).size() != SIZE) + throw new IllegalArgumentException("[ERROR] 중복되지 않은 번호여야 합니다."); + if (!numbers.stream().allMatch(n -> n >= MIN && n <= MAX)) + throw new IllegalArgumentException("[ERROR] 번호는 1~45 사이여야 합니다."); + } + + private List sorted(List numbers) { + return numbers.stream().sorted().toList(); + } + + public int matchCount(Set winning) { + return (int) numbers.stream().filter(winning::contains).count(); + } + + public boolean hasBonus(int bonus) { + return numbers.contains(bonus); + } + + public List getNumbers() { + return List.copyOf(numbers); + } + + @Override + public String toString() { + return numbers.toString(); + } +} diff --git a/src/main/java/lotto/model/LottoGenerator.java b/src/main/java/lotto/model/LottoGenerator.java new file mode 100644 index 0000000..334a2aa --- /dev/null +++ b/src/main/java/lotto/model/LottoGenerator.java @@ -0,0 +1,22 @@ +package lotto.model; + +import java.util.*; + +public class LottoGenerator { + public static Lotto generate() { + Set set = new HashSet<>(); + Random rand = new Random(); + while (set.size() < 6) { + set.add(rand.nextInt(45) + 1); + } + return new Lotto(new ArrayList<>(set)); + } + + public static List generateMultiple(int count) { + List list = new ArrayList<>(); + for (int i = 0; i < count; i++) { + list.add(generate()); + } + return list; + } +} diff --git a/src/main/java/lotto/model/LottoResult.java b/src/main/java/lotto/model/LottoResult.java new file mode 100644 index 0000000..e17cf3c --- /dev/null +++ b/src/main/java/lotto/model/LottoResult.java @@ -0,0 +1,34 @@ +package lotto.model; + +import java.util.*; + +public class LottoResult { + private final Map results = new LinkedHashMap<>(); + private int totalPrize = 0; + + public LottoResult() { + for (PrizeTier tier : PrizeTier.values()) { + results.put(tier, 0); + } + } + + public void add(Lotto lotto, Set winning, int bonus) { + int match = lotto.matchCount(winning); + boolean hasBonus = lotto.hasBonus(bonus); + PrizeTier tier = PrizeTier.valueOf(match, hasBonus); + if (tier == null) return; + + results.put(tier, results.get(tier) + 1); + totalPrize += tier.getPrize(); + } + + public void printStats() { + results.forEach((tier, count) -> + System.out.printf("%s - %d개%n", tier.getLabel(), count) + ); + } + + public int getTotalPrize() { + return totalPrize; + } +} diff --git a/src/main/java/lotto/model/PrizeTier.java b/src/main/java/lotto/model/PrizeTier.java new file mode 100644 index 0000000..2dca80a --- /dev/null +++ b/src/main/java/lotto/model/PrizeTier.java @@ -0,0 +1,36 @@ +package lotto.model; + +public enum PrizeTier { + FIRST(6, false, 2_000_000_000, "6개 일치 (2,000,000,000원)"), + SECOND(5, true, 30_000_000, "5개 일치, 보너스 볼 일치 (30,000,000원)"), + THIRD(5, false, 1_500_000, "5개 일치 (1,500,000원)"), + FOURTH(4, false, 50_000, "4개 일치 (50,000원)"), + FIFTH(3, false, 5_000, "3개 일치 (5,000원)"); + + private final int match; + private final boolean bonus; + private final int prize; + private final String label; + + PrizeTier(int match, boolean bonus, int prize, String label) { + this.match = match; + this.bonus = bonus; + this.prize = prize; + this.label = label; + } + + public static PrizeTier valueOf(int match, boolean hasBonus) { + for (PrizeTier tier : values()) { + if (tier.match == match && tier.bonus == hasBonus) return tier; + } + return null; + } + + public String getLabel() { + return label; + } + + public int getPrize() { + return prize; + } +} diff --git a/src/main/java/lotto/view/LottoView.java b/src/main/java/lotto/view/LottoView.java new file mode 100644 index 0000000..d62c107 --- /dev/null +++ b/src/main/java/lotto/view/LottoView.java @@ -0,0 +1,55 @@ +package lotto.view; + +import lotto.model.*; + +import java.util.*; + +public class LottoView { + private final Scanner sc = new Scanner(System.in); + + public int askMoney() { + System.out.println("로또 구입 금액을 입력해 주세요."); + int money = Integer.parseInt(sc.nextLine()); + if (money % 1000 != 0) + throw new IllegalArgumentException("[ERROR] 구입 금액은 1,000원 단위여야 합니다."); + return money; + } + + public void printTickets(List tickets) { + System.out.printf("%n%d개를 구매했습니다.%n", tickets.size()); + tickets.forEach(System.out::println); + } + + public Set askWinningNumbers() { + System.out.println("\n당첨 번호를 입력해 주세요."); + String[] tokens = sc.nextLine().split(","); + Set numbers = new HashSet<>(); + for (String token : tokens) { + int n = Integer.parseInt(token.trim()); + if (n < 1 || n > 45) throw new IllegalArgumentException("[ERROR] 당첨 번호는 1~45 사이여야 합니다."); + if (!numbers.add(n)) throw new IllegalArgumentException("[ERROR] 중복된 번호입니다."); + } + if (numbers.size() != 6) + throw new IllegalArgumentException("[ERROR] 당첨 번호는 6개여야 합니다."); + return numbers; + } + + public int askBonusNumber(Set winning) { + System.out.println("\n보너스 번호를 입력해 주세요."); + int bonus = Integer.parseInt(sc.nextLine()); + if (bonus < 1 || bonus > 45 || winning.contains(bonus)) + throw new IllegalArgumentException("[ERROR] 보너스 번호는 1~45 범위이며 당첨 번호와 중복되지 않아야 합니다."); + return bonus; + } + + public void printResult(LottoResult result, int money) { + System.out.println("\n당첨 통계\n---"); + result.printStats(); + double rate = ((double) result.getTotalPrize() / money) * 100; + System.out.printf("총 수익률은 %.1f%%입니다.%n", rate); + } + + public void printError(String msg) { + System.out.println(msg); + } +}