From c15d501fa308e4d40ddc21ad3f47c0e159a32c6f Mon Sep 17 00:00:00 2001 From: Kim HyeJi <83345092+khyej@users.noreply.github.com> Date: Thu, 5 Mar 2026 11:59:28 +0900 Subject: [PATCH 01/81] =?UTF-8?q?docs:=20=EA=B8=B0=EB=8A=A5=20=EB=AC=B8?= =?UTF-8?q?=EC=84=9C=20=EC=9E=91=EC=84=B1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/README.md b/README.md index 1ff5f7b6790..20838e77031 100644 --- a/README.md +++ b/README.md @@ -1,3 +1,24 @@ # java-blackjack 블랙잭 미션 저장소 + +--- + +### 구현 기능 목록 +1. [입력] 게임에 참여할 사람의 이름을 입력 받는다.(쉼표 기준으로 분리) + [예외처리] 쉼표 외의 다른 문자를 구분자로 한 경우 IllegalArgumentException 예외를 발생시킨다. + [예외처리] 입력값이 공백일 경우 IllegalArgumentException 예외를 발생시킨다. +2. [중간 과정] 딜러와 사용자에게 카드를 2장씩 나누어준다. + [카드 조건] 덱은 1개만 사용한다.(A ~ K : 13 * 4 = 52장) +3. [출력] 카드 현황을 출력한다. + [출력 조건] 딜러는 첫 번째 카드만 출력한다. +4. [입력] 사용자별로 카드 추가 지급 여부를 입력 받는다. + [예외처리] y, n 외의 다른 문자일 경우 IllegalArgumentException 예외를 발생시킨다. + [입력 조건] 모든 사용자가 추가 지급을 완료할 때까지 반복한다. +5. [출력] 사용자별로 지급 현황을 출력한다. +6. [출력] 딜러의 카드 합계가 17 이상이 일 될 때까지 추가 지급 현황을 출력한다. +7. [중간 과정] 카드 합계를 계산한다. + [ACE 조건] ACE가 11이어도 21이 넘지 않는 경우에는 11, 넘는 경우에는 1로 계산한다. +8. [출력] 사용자별 카드 현황 및 결과를 출력한다. +9. [중간 과정] 최종 승패 여부를 계산한다. +10. [출력] 최종 승패를 출력한다. From 5b1fa0f0a03443b44e676fbce905970f3a64877c Mon Sep 17 00:00:00 2001 From: khyej Date: Thu, 5 Mar 2026 12:00:08 +0900 Subject: [PATCH 02/81] =?UTF-8?q?feat:=20=EC=82=AC=EC=9A=A9=EC=9E=90=20?= =?UTF-8?q?=EC=9D=B4=EB=A6=84=20=EC=9E=85=EB=A0=A5=20=EA=B8=B0=EB=8A=A5=20?= =?UTF-8?q?=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/Application.java | 4 ++ .../controller/BlackjackController.java | 14 ++++++ src/main/java/blackjack/model/Dealer.java | 16 +++++++ src/main/java/blackjack/model/GameResult.java | 15 +++++++ src/main/java/blackjack/model/Player.java | 15 +++++++ src/main/java/blackjack/model/User.java | 13 ++++++ .../java/blackjack/util/PlayerParser.java | 32 ++++++++++++++ src/main/java/blackjack/view/InputView.java | 16 +++++++ .../java/blackjack/util/PlayerParserTest.java | 44 +++++++++++++++++++ 9 files changed, 169 insertions(+) create mode 100644 src/main/java/blackjack/Application.java create mode 100644 src/main/java/blackjack/controller/BlackjackController.java create mode 100644 src/main/java/blackjack/model/Dealer.java create mode 100644 src/main/java/blackjack/model/GameResult.java create mode 100644 src/main/java/blackjack/model/Player.java create mode 100644 src/main/java/blackjack/model/User.java create mode 100644 src/main/java/blackjack/util/PlayerParser.java create mode 100644 src/main/java/blackjack/view/InputView.java create mode 100644 src/test/java/blackjack/util/PlayerParserTest.java diff --git a/src/main/java/blackjack/Application.java b/src/main/java/blackjack/Application.java new file mode 100644 index 00000000000..a5767526aa7 --- /dev/null +++ b/src/main/java/blackjack/Application.java @@ -0,0 +1,4 @@ +package blackjack; + +public class Application { +} diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java new file mode 100644 index 00000000000..5a5654491b3 --- /dev/null +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -0,0 +1,14 @@ +package blackjack.controller; + +import blackjack.model.Player; +import blackjack.util.PlayerParser; +import blackjack.view.InputView; +import java.util.List; + +public class BlackjackController { + + public void run() { + String input = InputView.readPlayerName(); + List players = PlayerParser.parse(input); + } +} diff --git a/src/main/java/blackjack/model/Dealer.java b/src/main/java/blackjack/model/Dealer.java new file mode 100644 index 00000000000..feb5c04bb48 --- /dev/null +++ b/src/main/java/blackjack/model/Dealer.java @@ -0,0 +1,16 @@ +package blackjack.model; + +import java.util.EnumMap; + +public class Dealer extends User { + private EnumMap gameResults; + + public Dealer(String name) { + super(name); + gameResults = new EnumMap<>(GameResult.class); + } + + public EnumMap getGameResults() { + return gameResults; + } +} diff --git a/src/main/java/blackjack/model/GameResult.java b/src/main/java/blackjack/model/GameResult.java new file mode 100644 index 00000000000..ec75683f550 --- /dev/null +++ b/src/main/java/blackjack/model/GameResult.java @@ -0,0 +1,15 @@ +package blackjack.model; + +public enum GameResult { + + WIN("승"), + DRAW("무"), + LOSE("패"), + ; + + private final String format; + + GameResult(String format) { + this.format = format; + } +} diff --git a/src/main/java/blackjack/model/Player.java b/src/main/java/blackjack/model/Player.java new file mode 100644 index 00000000000..2afb553035d --- /dev/null +++ b/src/main/java/blackjack/model/Player.java @@ -0,0 +1,15 @@ +package blackjack.model; + + +public class Player extends User { + private GameResult gameResult; + + public Player(String name) { + super(name); + this.gameResult = GameResult.DRAW; + } + + public GameResult getGameResult() { + return gameResult; + } +} diff --git a/src/main/java/blackjack/model/User.java b/src/main/java/blackjack/model/User.java new file mode 100644 index 00000000000..26724bd152c --- /dev/null +++ b/src/main/java/blackjack/model/User.java @@ -0,0 +1,13 @@ +package blackjack.model; + +public class User { + private final String name; + + public User(String name) { + this.name = name; + } + + public String getName() { + return name; + } +} diff --git a/src/main/java/blackjack/util/PlayerParser.java b/src/main/java/blackjack/util/PlayerParser.java new file mode 100644 index 00000000000..0150bab270c --- /dev/null +++ b/src/main/java/blackjack/util/PlayerParser.java @@ -0,0 +1,32 @@ +package blackjack.util; + +import blackjack.model.Player; +import java.util.Arrays; +import java.util.List; +import java.util.regex.Pattern; + +public class PlayerParser { + + private static final String regrex = "^[a-zA-Z가-힣]*$"; + + public static List parse(String names) { + return Arrays.stream(names.split(",")) + .map(String::trim) + .peek(PlayerParser::validateRegrex) + .peek(PlayerParser::validateEmpty) + .map(Player::new) + .toList(); + } + + private static void validateRegrex(String parsedName) { + if (!Pattern.matches(regrex, parsedName)) { + throw new IllegalArgumentException("플레이어의 이름은 영어 or 한글로만 이루어질 수 있습니다."); + } + } + + private static void validateEmpty(String parsedName) { + if (parsedName.isEmpty()) { + throw new IllegalArgumentException("플레이어의 이름은 공백일 수 없습니다."); + } + } +} diff --git a/src/main/java/blackjack/view/InputView.java b/src/main/java/blackjack/view/InputView.java new file mode 100644 index 00000000000..90a78c08083 --- /dev/null +++ b/src/main/java/blackjack/view/InputView.java @@ -0,0 +1,16 @@ +package blackjack.view; + +import java.util.Scanner; + +public class InputView { + private static final Scanner sc = new Scanner(System.in); + + public static String readPlayerName() { + System.out.println("게임에 참여할 사람의 이름을 입력하세요.(쉼표 기준으로 분리)"); + return sc.nextLine(); + } + + public static void closeScanner() { + sc.close(); + } +} diff --git a/src/test/java/blackjack/util/PlayerParserTest.java b/src/test/java/blackjack/util/PlayerParserTest.java new file mode 100644 index 00000000000..f46f177f588 --- /dev/null +++ b/src/test/java/blackjack/util/PlayerParserTest.java @@ -0,0 +1,44 @@ +package blackjack.util; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import blackjack.model.Player; +import java.util.List; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.ValueSource; + +class PlayerParserTest { + + @Test + @DisplayName("플레이어 이름 파싱 및 플레이어 객체 생성") + void test_parse_success() { + String input = "pobi,james"; + + List players = PlayerParser.parse(input); + + assertThat(players.size()).isEqualTo(2); + assertThat(players) + .extracting("name") + .contains("pobi", "james"); + } + + @Test + @DisplayName("플레이어의 이름에 영어와 한글이 아닌 문자가 존재하는 경우 예외 발생") + void test_parse_fail_when_invalid_name() { + String invalidInput = "pobi,james*"; + + assertThatThrownBy(() -> PlayerParser.parse(invalidInput)) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @ValueSource(strings = {"", " ", " , , "}) + @DisplayName("플레이어의 이름이 공백인 경우 예외 발생") + void test_parse_fail_when_name_is_null(String emptyName) { + assertThatThrownBy(() -> PlayerParser.parse(emptyName)) + .isInstanceOf(IllegalArgumentException.class); + } +} \ No newline at end of file From 6914d5ecbe9c4e2ce00b751fb1d3bbd4bc558c07 Mon Sep 17 00:00:00 2001 From: khyej Date: Thu, 5 Mar 2026 17:15:32 +0900 Subject: [PATCH 03/81] =?UTF-8?q?feat:=20=EC=B9=B4=EB=93=9C=20=EC=B5=9C?= =?UTF-8?q?=EC=B4=88=20=EB=B0=B0=EB=B6=84=20=EA=B8=B0=EB=8A=A5=20=EA=B5=AC?= =?UTF-8?q?=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/Card.java | 76 +++++++++++++++++++ .../java/blackjack/model/CardProvider.java | 34 +++++++++ src/main/java/blackjack/model/CardStatus.java | 33 ++++++++ src/main/java/blackjack/model/Dealer.java | 4 +- src/main/java/blackjack/model/User.java | 11 +++ .../blackjack/model/CardProviderTest.java | 26 +++++++ 6 files changed, 182 insertions(+), 2 deletions(-) create mode 100644 src/main/java/blackjack/model/Card.java create mode 100644 src/main/java/blackjack/model/CardProvider.java create mode 100644 src/main/java/blackjack/model/CardStatus.java create mode 100644 src/test/java/blackjack/model/CardProviderTest.java diff --git a/src/main/java/blackjack/model/Card.java b/src/main/java/blackjack/model/Card.java new file mode 100644 index 00000000000..ba1a10d41be --- /dev/null +++ b/src/main/java/blackjack/model/Card.java @@ -0,0 +1,76 @@ +package blackjack.model; + +public enum Card { + A_SPADE(1, "A스페이드"), + TWO_SPADE(2, "2스페이드"), + THREE_SPADE(3, "3스페이드"), + FOUR_SPADE(4, "4스페이드"), + FIVE_SPADE(5, "5스페이드"), + SIX_SPADE(6, "6스페이드"), + SEVEN_SPADE(7, "7스페이드"), + EIGHT_SPADE(8, "8스페이드"), + NINE_SPADE(9, "9스페이드"), + TEN_SPADE(10, "10스페이드"), + J_SPADE(10, "J스페이드"), + Q_SPADE(10, "Q스페이드"), + K_SPADE(10, "K스페이드"), + + A_HEART(1, "A하트"), + TWO_HEART(2, "2하트"), + THREE_HEART(3, "3하트"), + FOUR_HEART(4, "4하트"), + FIVE_HEART(5, "5하트"), + SIX_HEART(6, "6하트"), + SEVEN_HEART(7, "7하트"), + EIGHT_HEART(8, "8하트"), + NINE_HEART(9, "9하트"), + TEN_HEART(10, "10하트"), + J_HEART(10, "J하트"), + Q_HEART(10, "Q하트"), + K_HEART(10, "K하트"), + + A_CLOVER(1, "A클로버"), + TWO_CLOVER(2, "2클로버"), + THREE_CLOVER(3, "3클로버"), + FOUR_CLOVER(4, "4클로버"), + FIVE_CLOVER(5, "5클로버"), + SIX_CLOVER(6, "6클로버"), + SEVEN_CLOVER(7, "7클로버"), + EIGHT_CLOVER(8, "8클로버"), + NINE_CLOVER(9, "9클로버"), + TEN_CLOVER(10, "10클로버"), + J_CLOVER(10, "J클로버"), + Q_CLOVER(10, "Q클로버"), + K_CLOVER(10, "K클로버"), + + A_DIA(1, "A다이아몬드"), + TWO_DIA(2, "2다이아몬드"), + THREE_DIA(3, "3다이아몬드"), + FOUR_DIA(4, "4다이아몬드"), + FIVE_DIA(5, "5다이아몬드"), + SIX_DIA(6, "6다이아몬드"), + SEVEN_DIA(7, "7다이아몬드"), + EIGHT_DIA(8, "8다이아몬드"), + NINE_DIA(9, "9다이아몬드"), + TEN_DIA(10, "10다이아몬드"), + J_DIA(10, "J다이아몬드"), + Q_DIA(10, "Q다이아몬드"), + K_DIA(10, "K다이아몬드"), + ; + + private int number; + private String format; + + Card(int number, String format) { + this.number = number; + this.format = format; + } + + public int getNumber() { + return number; + } + + public String getFormat() { + return format; + } +} \ No newline at end of file diff --git a/src/main/java/blackjack/model/CardProvider.java b/src/main/java/blackjack/model/CardProvider.java new file mode 100644 index 00000000000..6ca8bdc6ab4 --- /dev/null +++ b/src/main/java/blackjack/model/CardProvider.java @@ -0,0 +1,34 @@ +package blackjack.model; + +import java.util.ArrayList; +import java.util.Collections; +import java.util.LinkedList; +import java.util.List; +import java.util.Queue; + +public class CardProvider { + private final Queue deck = new LinkedList<>(); + + public CardProvider() { + initDeck(); + } + + private void initDeck() { + List cards = new ArrayList<>(); + for (Card card : Card.values()) { + cards.add(card); + } + Collections.shuffle(cards); + this.deck.addAll(cards); + } + + public void provideInitCards(List players, Dealer dealer) { + for (int i = 0; i < 2; i++) { + for (Player player : players) { + player.addCard(deck.poll()); + } + dealer.addCard(deck.poll()); + } + } + +} diff --git a/src/main/java/blackjack/model/CardStatus.java b/src/main/java/blackjack/model/CardStatus.java new file mode 100644 index 00000000000..0eda9cff30a --- /dev/null +++ b/src/main/java/blackjack/model/CardStatus.java @@ -0,0 +1,33 @@ +package blackjack.model; + +import java.util.ArrayList; +import java.util.List; + +public class CardStatus { + + private final List cards; + private int totalScore; + private boolean blackjack; + + public CardStatus() { + this.cards = new ArrayList<>(); + this.totalScore = 0; + this.blackjack = false; + } + + public List getCards() { + return cards; + } + + public int getTotalScore() { + return totalScore; + } + + public boolean isBlackjack() { + return blackjack; + } + + public void addCard(Card card) { + cards.add(card); + } +} diff --git a/src/main/java/blackjack/model/Dealer.java b/src/main/java/blackjack/model/Dealer.java index feb5c04bb48..548eae94d20 100644 --- a/src/main/java/blackjack/model/Dealer.java +++ b/src/main/java/blackjack/model/Dealer.java @@ -5,8 +5,8 @@ public class Dealer extends User { private EnumMap gameResults; - public Dealer(String name) { - super(name); + public Dealer() { + super("딜러"); gameResults = new EnumMap<>(GameResult.class); } diff --git a/src/main/java/blackjack/model/User.java b/src/main/java/blackjack/model/User.java index 26724bd152c..964402dbe41 100644 --- a/src/main/java/blackjack/model/User.java +++ b/src/main/java/blackjack/model/User.java @@ -1,13 +1,24 @@ package blackjack.model; public class User { + private final String name; + private final CardStatus cardStatus; public User(String name) { this.name = name; + this.cardStatus = new CardStatus(); } public String getName() { return name; } + + public CardStatus getCardStatus() { + return cardStatus; + } + + public void addCard(Card card) { + cardStatus.addCard(card); + } } diff --git a/src/test/java/blackjack/model/CardProviderTest.java b/src/test/java/blackjack/model/CardProviderTest.java new file mode 100644 index 00000000000..d186e25fb67 --- /dev/null +++ b/src/test/java/blackjack/model/CardProviderTest.java @@ -0,0 +1,26 @@ +package blackjack.model; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.List; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +class CardProviderTest { + + @Test + @DisplayName("딜러 및 플레이어에게 초기 카드 2장 정상 배분") + void test_provide_init_cards() { + CardProvider cardProvider = new CardProvider(); + + List players = List.of(new Player("pobi"), new Player("james")); + Dealer dealer = new Dealer(); + + cardProvider.provideInitCards(players, dealer); + + for (Player player : players) { + assertThat(player.getCardStatus().getCards().size()).isEqualTo(2); + } + assertThat(dealer.getCardStatus().getCards().size()).isEqualTo(2); + } +} \ No newline at end of file From 54d9be663772b046ab8e4a2c0200eeab24b59173 Mon Sep 17 00:00:00 2001 From: khyej Date: Thu, 5 Mar 2026 17:18:12 +0900 Subject: [PATCH 04/81] =?UTF-8?q?feat:=20=EC=B5=9C=EC=B4=88=20=EC=B9=B4?= =?UTF-8?q?=EB=93=9C=20=ED=98=84=ED=99=A9=20=EC=B6=9C=EB=A0=A5=20=EA=B8=B0?= =?UTF-8?q?=EB=8A=A5=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/view/OutputView.java | 36 ++++++++++++++++++++ 1 file changed, 36 insertions(+) create mode 100644 src/main/java/blackjack/view/OutputView.java diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java new file mode 100644 index 00000000000..0448a41aca3 --- /dev/null +++ b/src/main/java/blackjack/view/OutputView.java @@ -0,0 +1,36 @@ +package blackjack.view; + +import blackjack.model.Card; +import blackjack.model.Dealer; +import blackjack.model.Player; +import java.util.List; + +public class OutputView { + public static void printInitCards(List players, Dealer dealer) { + List names = players.stream() + .map(Player::getName) + .toList(); + StringBuilder sb = new StringBuilder(); + sb.append("딜러와 "); + sb.append(String.join(", ", names)); + sb.append("에게 2장을 나누었습니다."); + System.out.println(sb); + + printDealerCard(dealer); + for (Player player : players) { + printPlayerCards(player); + } + } + + private static void printDealerCard(Dealer dealer) { + System.out.println("딜러카드: " + dealer.getCardStatus().getCards().getFirst().getFormat()); + } + + public static void printPlayerCards(Player player) { + List formats = player.getCardStatus().getCards().stream() + .map(Card::getFormat) + .toList(); + + System.out.println(player.getName() + "카드: " + String.join(", ", formats)); + } +} From 219ee2912054f7a9e139d61ea39dc21f7669869b Mon Sep 17 00:00:00 2001 From: khyej Date: Thu, 5 Mar 2026 17:59:06 +0900 Subject: [PATCH 05/81] =?UTF-8?q?feat:=20=EC=B9=B4=EB=93=9C=20=EC=B6=94?= =?UTF-8?q?=EA=B0=80=20=EC=A7=80=EA=B8=89=20=EA=B8=B0=EB=8A=A5=20=EA=B5=AC?= =?UTF-8?q?=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 16 ++++--- .../controller/BlackjackController.java | 41 +++++++++++++++++ .../java/blackjack/model/CardCalculator.java | 38 ++++++++++++++++ .../java/blackjack/model/CardProvider.java | 7 +++ src/main/java/blackjack/view/InputView.java | 6 +++ src/main/java/blackjack/view/OutputView.java | 8 ++++ .../blackjack/model/CardCalculatorTest.java | 33 ++++++++++++++ .../blackjack/model/CardProviderTest.java | 45 ++++++++++++++++++- 8 files changed, 186 insertions(+), 8 deletions(-) create mode 100644 src/main/java/blackjack/model/CardCalculator.java create mode 100644 src/test/java/blackjack/model/CardCalculatorTest.java diff --git a/README.md b/README.md index 20838e77031..2281a2f2757 100644 --- a/README.md +++ b/README.md @@ -5,20 +5,22 @@ --- ### 구현 기능 목록 + 1. [입력] 게임에 참여할 사람의 이름을 입력 받는다.(쉼표 기준으로 분리) - [예외처리] 쉼표 외의 다른 문자를 구분자로 한 경우 IllegalArgumentException 예외를 발생시킨다. - [예외처리] 입력값이 공백일 경우 IllegalArgumentException 예외를 발생시킨다. + [예외처리] 쉼표 외의 다른 문자를 구분자로 한 경우 IllegalArgumentException 예외를 발생시킨다. + [예외처리] 입력값이 공백일 경우 IllegalArgumentException 예외를 발생시킨다. 2. [중간 과정] 딜러와 사용자에게 카드를 2장씩 나누어준다. - [카드 조건] 덱은 1개만 사용한다.(A ~ K : 13 * 4 = 52장) + [카드 조건] 덱은 1개만 사용한다.(A ~ K : 13 * 4 = 52장) 3. [출력] 카드 현황을 출력한다. - [출력 조건] 딜러는 첫 번째 카드만 출력한다. + [출력 조건] 딜러는 첫 번째 카드만 출력한다. 4. [입력] 사용자별로 카드 추가 지급 여부를 입력 받는다. - [예외처리] y, n 외의 다른 문자일 경우 IllegalArgumentException 예외를 발생시킨다. - [입력 조건] 모든 사용자가 추가 지급을 완료할 때까지 반복한다. + [예외처리] y, n 외의 다른 문자일 경우 IllegalArgumentException 예외를 발생시킨다. + [입력 조건] 모든 사용자가 추가 지급을 완료할 때까지 반복한다. + [지급 조건] 사용자가 y를 입력하고, 사용자의 현재 카드 합계가 21미만일 경우에 카드를 지급한다. 5. [출력] 사용자별로 지급 현황을 출력한다. 6. [출력] 딜러의 카드 합계가 17 이상이 일 될 때까지 추가 지급 현황을 출력한다. 7. [중간 과정] 카드 합계를 계산한다. - [ACE 조건] ACE가 11이어도 21이 넘지 않는 경우에는 11, 넘는 경우에는 1로 계산한다. + [ACE 조건] ACE가 11이어도 21이 넘지 않는 경우에는 11, 넘는 경우에는 1로 계산한다. 8. [출력] 사용자별 카드 현황 및 결과를 출력한다. 9. [중간 과정] 최종 승패 여부를 계산한다. 10. [출력] 최종 승패를 출력한다. diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index 5a5654491b3..ec353668e94 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -1,14 +1,55 @@ package blackjack.controller; +import blackjack.model.CardCalculator; +import blackjack.model.CardProvider; +import blackjack.model.Dealer; import blackjack.model.Player; import blackjack.util.PlayerParser; import blackjack.view.InputView; +import blackjack.view.OutputView; import java.util.List; public class BlackjackController { + private final CardProvider cardProvider; + private final CardCalculator cardCalculator; + + public BlackjackController(CardProvider cardProvider, CardCalculator cardCalculator) { + this.cardProvider = cardProvider; + this.cardCalculator = cardCalculator; + } + public void run() { String input = InputView.readPlayerName(); List players = PlayerParser.parse(input); + Dealer dealer = new Dealer(); + + cardProvider.provideInitCards(players, dealer); + OutputView.printInitCards(players, dealer); + + hit(players, dealer); + } + + public void hit(List players, Dealer dealer) { + + for (Player player : players) { + while (InputView.readCardAdd(player).equals("y") && checkAddCard(player, cardCalculator)) { + cardProvider.provideOneCard(player); + OutputView.printPlayerCards(player); + } + } + + while (cardCalculator.totalScore(dealer.getCardStatus().getCards()) < 17) { + OutputView.printDealerHit(); + cardProvider.provideOneCard(dealer); + } + } + + private boolean checkAddCard(Player player, CardCalculator cardCalculator) { + if (cardProvider.isGreaterThanTwentyOne(player, cardCalculator)) { + OutputView.printCantAddCard(); + return false; + } + return true; } } diff --git a/src/main/java/blackjack/model/CardCalculator.java b/src/main/java/blackjack/model/CardCalculator.java new file mode 100644 index 00000000000..d2bf7f23fed --- /dev/null +++ b/src/main/java/blackjack/model/CardCalculator.java @@ -0,0 +1,38 @@ +package blackjack.model; + +import java.util.List; +import java.util.Map; +import java.util.stream.Collectors; + +public class CardCalculator { + + public int totalScore(List cards) { + Map> partitioned = cards.stream() + .collect(Collectors.partitioningBy(card -> + card.equals(Card.A_CLOVER) || + card.equals(Card.A_DIA) || + card.equals(Card.A_SPADE) || + card.equals(Card.A_HEART) + )); + + List aceCards = partitioned.get(true); // Ace인 카드들 + List nonAceCards = partitioned.get(false);// Ace가 아닌 카드들 + int totalScoreNonAce = nonAceCards.stream() + .mapToInt(Card::getNumber) + .sum(); + + return getTotalScore(aceCards, totalScoreNonAce); + } + + int getTotalScore(List aceCards, int totalScore) { + for (int i = 0; i < aceCards.size(); i++) { + if (totalScore + 11 > 21) { + totalScore += 1; + continue; + } + totalScore += 11; + } + + return totalScore; + } +} \ No newline at end of file diff --git a/src/main/java/blackjack/model/CardProvider.java b/src/main/java/blackjack/model/CardProvider.java index 6ca8bdc6ab4..1cc0f94a553 100644 --- a/src/main/java/blackjack/model/CardProvider.java +++ b/src/main/java/blackjack/model/CardProvider.java @@ -31,4 +31,11 @@ public void provideInitCards(List players, Dealer dealer) { } } + public void provideOneCard(User user) { + user.addCard(deck.poll()); + } + + public boolean isGreaterThanTwentyOne(Player player, CardCalculator cardCalculator) { + return cardCalculator.totalScore(player.getCardStatus().getCards()) >= 21; + } } diff --git a/src/main/java/blackjack/view/InputView.java b/src/main/java/blackjack/view/InputView.java index 90a78c08083..de3226e05d6 100644 --- a/src/main/java/blackjack/view/InputView.java +++ b/src/main/java/blackjack/view/InputView.java @@ -1,5 +1,6 @@ package blackjack.view; +import blackjack.model.Player; import java.util.Scanner; public class InputView { @@ -10,6 +11,11 @@ public static String readPlayerName() { return sc.nextLine(); } + public static String readCardAdd(Player player) { + System.out.println(player.getName() + "는 한장의 카드를 더 받겠습니까?(예는 y, 아니오는 n)"); + return sc.nextLine(); + } + public static void closeScanner() { sc.close(); } diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index 0448a41aca3..13d2fa9ae3a 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -33,4 +33,12 @@ public static void printPlayerCards(Player player) { System.out.println(player.getName() + "카드: " + String.join(", ", formats)); } + + public static void printCantAddCard() { + System.out.println("카드의 합계가 21 이상입니다. 더이상 카드를 받을 수 없습니다."); + } + + public static void printDealerHit() { + System.out.println("딜러는 16이하라 한장의 카드를 더 받았습니다."); + } } diff --git a/src/test/java/blackjack/model/CardCalculatorTest.java b/src/test/java/blackjack/model/CardCalculatorTest.java new file mode 100644 index 00000000000..b02185fd063 --- /dev/null +++ b/src/test/java/blackjack/model/CardCalculatorTest.java @@ -0,0 +1,33 @@ +package blackjack.model; + +import java.util.List; +import org.assertj.core.api.Assertions; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +class CardCalculatorTest { + + @Test + @DisplayName("카드의 총합이 10 이하일 경우 ace 카드의 점수는 11") + void test_getTotalScore_when_ace_is_eleven() { + List aceCards = List.of(Card.A_SPADE); + int totalScore = 10; + CardCalculator cardCalculator = new CardCalculator(); + + int result = cardCalculator.getTotalScore(aceCards, totalScore); + + Assertions.assertThat(result).isEqualTo(totalScore + 11); + } + + @Test + @DisplayName("카드의 총합이 11 이상일 경우 ace 카드의 점수는 1") + void test_getTotalScore_when_ace_is_one() { + List aceCards = List.of(Card.A_SPADE); + int totalScore = 11; + CardCalculator cardCalculator = new CardCalculator(); + + int result = cardCalculator.getTotalScore(aceCards, totalScore); + + Assertions.assertThat(result).isEqualTo(totalScore + 1); + } +} \ No newline at end of file diff --git a/src/test/java/blackjack/model/CardProviderTest.java b/src/test/java/blackjack/model/CardProviderTest.java index d186e25fb67..78e46613188 100644 --- a/src/test/java/blackjack/model/CardProviderTest.java +++ b/src/test/java/blackjack/model/CardProviderTest.java @@ -15,7 +15,7 @@ void test_provide_init_cards() { List players = List.of(new Player("pobi"), new Player("james")); Dealer dealer = new Dealer(); - + cardProvider.provideInitCards(players, dealer); for (Player player : players) { @@ -23,4 +23,47 @@ void test_provide_init_cards() { } assertThat(dealer.getCardStatus().getCards().size()).isEqualTo(2); } + + @Test + @DisplayName("카드 추가 지급 성공") + void test_provide_one_card_success() { + Player player = new Player("pobi"); + CardProvider cardProvider = new CardProvider(); + + cardProvider.provideOneCard(player); + + assertThat(player.getCardStatus().getCards().size()).isEqualTo(1); + } + + + @Test + @DisplayName("플레이어의 카드 합계까 21 이상인 경우 true 반환") + void test_isGreaterThanTwentyOne_return_true() { + Player player = new Player("pobi"); + CardCalculator cardCalculator = new CardCalculator(); + CardProvider cardProvider = new CardProvider(); + + player.addCard(Card.A_DIA); + player.addCard(Card.J_DIA); + player.addCard(Card.Q_CLOVER); + + boolean result = cardProvider.isGreaterThanTwentyOne(player, cardCalculator); + + assertThat(result).isTrue(); + } + + @Test + @DisplayName("플레이어의 카드 합계까 21 미만인 경우 false 반환") + void test_isGreaterThanTwentyOne_return_false() { + Player player = new Player("pobi"); + CardCalculator cardCalculator = new CardCalculator(); + CardProvider cardProvider = new CardProvider(); + + player.addCard(Card.J_DIA); + player.addCard(Card.Q_CLOVER); + + boolean result = cardProvider.isGreaterThanTwentyOne(player, cardCalculator); + + assertThat(result).isFalse(); + } } \ No newline at end of file From 8e6ad0aa76cecfdcceea19883aa003e3123a2296 Mon Sep 17 00:00:00 2001 From: khyej Date: Thu, 5 Mar 2026 18:18:05 +0900 Subject: [PATCH 06/81] =?UTF-8?q?refactor:=20CardProvider=20=EC=97=AD?= =?UTF-8?q?=ED=95=A0=20=EB=B6=84=EB=A6=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/controller/BlackjackController.java | 2 +- src/main/java/blackjack/model/CardProvider.java | 4 ---- 2 files changed, 1 insertion(+), 5 deletions(-) diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index ec353668e94..addc3b5db49 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -46,7 +46,7 @@ public void hit(List players, Dealer dealer) { } private boolean checkAddCard(Player player, CardCalculator cardCalculator) { - if (cardProvider.isGreaterThanTwentyOne(player, cardCalculator)) { + if (cardCalculator.totalScore(player.getCardStatus().getCards()) >= 21) { OutputView.printCantAddCard(); return false; } diff --git a/src/main/java/blackjack/model/CardProvider.java b/src/main/java/blackjack/model/CardProvider.java index 1cc0f94a553..4bc119b5a32 100644 --- a/src/main/java/blackjack/model/CardProvider.java +++ b/src/main/java/blackjack/model/CardProvider.java @@ -34,8 +34,4 @@ public void provideInitCards(List players, Dealer dealer) { public void provideOneCard(User user) { user.addCard(deck.poll()); } - - public boolean isGreaterThanTwentyOne(Player player, CardCalculator cardCalculator) { - return cardCalculator.totalScore(player.getCardStatus().getCards()) >= 21; - } } From 89911aa5c0162fd4f28eee82696db9592a51b2c7 Mon Sep 17 00:00:00 2001 From: khyej Date: Thu, 5 Mar 2026 18:18:49 +0900 Subject: [PATCH 07/81] =?UTF-8?q?refactor:=20=EB=B2=84=EC=8A=A4=ED=8A=B8?= =?UTF-8?q?=20=EC=97=AC=EB=B6=80=20=EB=B3=80=EC=88=98=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/CardStatus.java | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/main/java/blackjack/model/CardStatus.java b/src/main/java/blackjack/model/CardStatus.java index 0eda9cff30a..f9214030ad2 100644 --- a/src/main/java/blackjack/model/CardStatus.java +++ b/src/main/java/blackjack/model/CardStatus.java @@ -7,12 +7,14 @@ public class CardStatus { private final List cards; private int totalScore; - private boolean blackjack; + private boolean isBlackjack; + private boolean isBust; public CardStatus() { this.cards = new ArrayList<>(); this.totalScore = 0; - this.blackjack = false; + this.isBlackjack = false; + this.isBust = false; } public List getCards() { From 3a0577d013adfebef1f46b9cb7f4591c76806b1a Mon Sep 17 00:00:00 2001 From: khyej Date: Thu, 5 Mar 2026 18:49:44 +0900 Subject: [PATCH 08/81] =?UTF-8?q?refactor:=20=EB=B3=80=EC=88=98=EB=AA=85?= =?UTF-8?q?=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/CardStatus.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/blackjack/model/CardStatus.java b/src/main/java/blackjack/model/CardStatus.java index f9214030ad2..1910c37c5bc 100644 --- a/src/main/java/blackjack/model/CardStatus.java +++ b/src/main/java/blackjack/model/CardStatus.java @@ -26,7 +26,7 @@ public int getTotalScore() { } public boolean isBlackjack() { - return blackjack; + return isBlackjack; } public void addCard(Card card) { From fd6108df99aefb44723a23ae2b7193303bb8c135 Mon Sep 17 00:00:00 2001 From: khyej Date: Thu, 5 Mar 2026 20:27:50 +0900 Subject: [PATCH 09/81] =?UTF-8?q?refactor:=20=EB=B8=94=EB=9E=99=EC=9E=AD?= =?UTF-8?q?=20=EA=B8=B0=EB=A1=9D=20=EB=B0=8F=20=EC=A1=B0=ED=9A=8C=20?= =?UTF-8?q?=EB=A9=94=EC=84=9C=EB=93=9C=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../blackjack/controller/BlackjackController.java | 10 ++++++++++ src/main/java/blackjack/model/CardStatus.java | 12 +++++++----- src/main/java/blackjack/model/User.java | 8 ++++++++ 3 files changed, 25 insertions(+), 5 deletions(-) diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index addc3b5db49..f04457fab7d 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -25,6 +25,7 @@ public void run() { Dealer dealer = new Dealer(); cardProvider.provideInitCards(players, dealer); + checkBlackjack(players, dealer); OutputView.printInitCards(players, dealer); hit(players, dealer); @@ -45,6 +46,15 @@ public void hit(List players, Dealer dealer) { } } + private void checkBlackjack(List players, Dealer dealer) { + for (Player player : players) { + if (cardCalculator.totalScore(player.getCardStatus().getCards()) == 21) { + player.markBlackjack(); + } + } + } + + private boolean checkAddCard(Player player, CardCalculator cardCalculator) { if (cardCalculator.totalScore(player.getCardStatus().getCards()) >= 21) { OutputView.printCantAddCard(); diff --git a/src/main/java/blackjack/model/CardStatus.java b/src/main/java/blackjack/model/CardStatus.java index 1910c37c5bc..a90cfe39c4e 100644 --- a/src/main/java/blackjack/model/CardStatus.java +++ b/src/main/java/blackjack/model/CardStatus.java @@ -7,14 +7,12 @@ public class CardStatus { private final List cards; private int totalScore; - private boolean isBlackjack; - private boolean isBust; + private boolean blackjack; public CardStatus() { this.cards = new ArrayList<>(); this.totalScore = 0; - this.isBlackjack = false; - this.isBust = false; + this.blackjack = false; } public List getCards() { @@ -26,10 +24,14 @@ public int getTotalScore() { } public boolean isBlackjack() { - return isBlackjack; + return blackjack; } public void addCard(Card card) { cards.add(card); } + + public void markBlackjack() { + this.blackjack = true; + } } diff --git a/src/main/java/blackjack/model/User.java b/src/main/java/blackjack/model/User.java index 964402dbe41..4727a9332ab 100644 --- a/src/main/java/blackjack/model/User.java +++ b/src/main/java/blackjack/model/User.java @@ -21,4 +21,12 @@ public CardStatus getCardStatus() { public void addCard(Card card) { cardStatus.addCard(card); } + + public void markBlackjack() { + cardStatus.markBlackjack(); + } + + public boolean isBlackjack() { + return cardStatus.isBlackjack(); + } } From 7dd3ffe658f1c4717164517463ccce3f0c1f0bae Mon Sep 17 00:00:00 2001 From: khyej Date: Thu, 5 Mar 2026 20:29:01 +0900 Subject: [PATCH 10/81] =?UTF-8?q?test:=20BlackjackController=20=EB=8B=A8?= =?UTF-8?q?=EC=9C=84=20=ED=85=8C=EC=8A=A4=ED=8A=B8=20=EC=9E=91=EC=84=B1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../controller/BlackjackController.java | 12 ++-- .../controller/BlackjackControllerTest.java | 60 +++++++++++++++++++ .../blackjack/model/CardProviderTest.java | 31 ---------- 3 files changed, 68 insertions(+), 35 deletions(-) create mode 100644 src/test/java/blackjack/controller/BlackjackControllerTest.java diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index f04457fab7d..b64a4259eaf 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -9,6 +9,7 @@ import blackjack.view.OutputView; import java.util.List; + public class BlackjackController { private final CardProvider cardProvider; @@ -32,9 +33,8 @@ public void run() { } public void hit(List players, Dealer dealer) { - for (Player player : players) { - while (InputView.readCardAdd(player).equals("y") && checkAddCard(player, cardCalculator)) { + while (InputView.readCardAdd(player).equals("y") && checkAddCard(player)) { cardProvider.provideOneCard(player); OutputView.printPlayerCards(player); } @@ -46,16 +46,20 @@ public void hit(List players, Dealer dealer) { } } - private void checkBlackjack(List players, Dealer dealer) { + void checkBlackjack(List players, Dealer dealer) { for (Player player : players) { if (cardCalculator.totalScore(player.getCardStatus().getCards()) == 21) { player.markBlackjack(); } } + + if (cardCalculator.totalScore(dealer.getCardStatus().getCards()) == 21) { + dealer.markBlackjack(); + } } - private boolean checkAddCard(Player player, CardCalculator cardCalculator) { + boolean checkAddCard(Player player) { if (cardCalculator.totalScore(player.getCardStatus().getCards()) >= 21) { OutputView.printCantAddCard(); return false; diff --git a/src/test/java/blackjack/controller/BlackjackControllerTest.java b/src/test/java/blackjack/controller/BlackjackControllerTest.java new file mode 100644 index 00000000000..7b36a9c316d --- /dev/null +++ b/src/test/java/blackjack/controller/BlackjackControllerTest.java @@ -0,0 +1,60 @@ +package blackjack.controller; + +import blackjack.model.Card; +import blackjack.model.CardCalculator; +import blackjack.model.CardProvider; +import blackjack.model.Dealer; +import blackjack.model.Player; +import java.util.List; +import org.assertj.core.api.Assertions; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +class BlackjackControllerTest { + private final CardProvider cardProvider = new CardProvider(); + private final CardCalculator cardCalculator = new CardCalculator(); + private final BlackjackController blackjackController = new BlackjackController(cardProvider, cardCalculator); + + @Test + @DisplayName("최초 배분 카드 두 장의 합이 21일 경우 블랙잭") + void test_checkBlackjack() { + Player player = new Player("pobi"); + List players = List.of(player); + Dealer dealer = new Dealer(); + + player.addCard(Card.A_CLOVER); + player.addCard(Card.J_DIA); + + dealer.addCard(Card.A_CLOVER); + dealer.addCard(Card.J_DIA); + + blackjackController.checkBlackjack(players, dealer); + + Assertions.assertThat(player.isBlackjack()).isTrue(); + Assertions.assertThat(dealer.isBlackjack()).isTrue(); + } + + + @Test + @DisplayName("카드의 합이 21이상인 경우 카드 추가 지급 불가 ( false 반환 )") + void test_checkAddCard_return_false() { + + Player player = new Player("pobi"); + player.addCard(Card.J_DIA); + player.addCard(Card.Q_CLOVER); + player.addCard(Card.TEN_HEART); + + Assertions.assertThat(blackjackController.checkAddCard(player)).isFalse(); + } + + @Test + @DisplayName("카드의 합이 21이상인 경우 카드 추가 지급 불가 ( false 반환 )") + void test_checkAddCard_return_true() { + + Player player = new Player("pobi"); + player.addCard(Card.J_DIA); + player.addCard(Card.Q_CLOVER); + + Assertions.assertThat(blackjackController.checkAddCard(player)).isTrue(); + } +} \ No newline at end of file diff --git a/src/test/java/blackjack/model/CardProviderTest.java b/src/test/java/blackjack/model/CardProviderTest.java index 78e46613188..6035188f9aa 100644 --- a/src/test/java/blackjack/model/CardProviderTest.java +++ b/src/test/java/blackjack/model/CardProviderTest.java @@ -35,35 +35,4 @@ void test_provide_one_card_success() { assertThat(player.getCardStatus().getCards().size()).isEqualTo(1); } - - @Test - @DisplayName("플레이어의 카드 합계까 21 이상인 경우 true 반환") - void test_isGreaterThanTwentyOne_return_true() { - Player player = new Player("pobi"); - CardCalculator cardCalculator = new CardCalculator(); - CardProvider cardProvider = new CardProvider(); - - player.addCard(Card.A_DIA); - player.addCard(Card.J_DIA); - player.addCard(Card.Q_CLOVER); - - boolean result = cardProvider.isGreaterThanTwentyOne(player, cardCalculator); - - assertThat(result).isTrue(); - } - - @Test - @DisplayName("플레이어의 카드 합계까 21 미만인 경우 false 반환") - void test_isGreaterThanTwentyOne_return_false() { - Player player = new Player("pobi"); - CardCalculator cardCalculator = new CardCalculator(); - CardProvider cardProvider = new CardProvider(); - - player.addCard(Card.J_DIA); - player.addCard(Card.Q_CLOVER); - - boolean result = cardProvider.isGreaterThanTwentyOne(player, cardCalculator); - - assertThat(result).isFalse(); - } } \ No newline at end of file From 0ce22d2790b9e9900a1955b5c311934458eaec82 Mon Sep 17 00:00:00 2001 From: khyej Date: Thu, 5 Mar 2026 20:32:57 +0900 Subject: [PATCH 11/81] =?UTF-8?q?docs:=20=EA=B8=B0=EB=8A=A5=20=EB=AA=A9?= =?UTF-8?q?=EB=A1=9D=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/README.md b/README.md index 2281a2f2757..75f79f000e9 100644 --- a/README.md +++ b/README.md @@ -11,16 +11,16 @@ [예외처리] 입력값이 공백일 경우 IllegalArgumentException 예외를 발생시킨다. 2. [중간 과정] 딜러와 사용자에게 카드를 2장씩 나누어준다. [카드 조건] 덱은 1개만 사용한다.(A ~ K : 13 * 4 = 52장) -3. [출력] 카드 현황을 출력한다. +3. [중간 과정] 딜러와 사용자의 최초 카드 합계를 구하며, 블랙잭 여부를 판단한다. + [ACE 조건] ACE가 11이어도 21이 넘지 않는 경우에는 11, 넘는 경우에는 1로 계산한다. +4. [출력] 카드 현황을 출력한다. [출력 조건] 딜러는 첫 번째 카드만 출력한다. -4. [입력] 사용자별로 카드 추가 지급 여부를 입력 받는다. +5. [입력] 사용자별로 카드 추가 지급 여부를 입력 받는다. [예외처리] y, n 외의 다른 문자일 경우 IllegalArgumentException 예외를 발생시킨다. [입력 조건] 모든 사용자가 추가 지급을 완료할 때까지 반복한다. [지급 조건] 사용자가 y를 입력하고, 사용자의 현재 카드 합계가 21미만일 경우에 카드를 지급한다. -5. [출력] 사용자별로 지급 현황을 출력한다. -6. [출력] 딜러의 카드 합계가 17 이상이 일 될 때까지 추가 지급 현황을 출력한다. -7. [중간 과정] 카드 합계를 계산한다. - [ACE 조건] ACE가 11이어도 21이 넘지 않는 경우에는 11, 넘는 경우에는 1로 계산한다. +6. [출력] 사용자별로 지급 현황을 출력한다. +7. [출력] 딜러의 카드 합계가 17 이상이 일 될 때까지 추가 지급 현황을 출력한다. 8. [출력] 사용자별 카드 현황 및 결과를 출력한다. 9. [중간 과정] 최종 승패 여부를 계산한다. 10. [출력] 최종 승패를 출력한다. From ccc2f7d25c689b903ea4ba6dd1c7371a2a4a33f8 Mon Sep 17 00:00:00 2001 From: khyej Date: Thu, 5 Mar 2026 20:44:54 +0900 Subject: [PATCH 12/81] =?UTF-8?q?feat:=20=EC=82=AC=EC=9A=A9=EC=9E=90?= =?UTF-8?q?=EB=B3=84=20=EC=B9=B4=EB=93=9C=20=ED=98=84=ED=99=A9=20=EB=B0=8F?= =?UTF-8?q?=20=ED=95=A9=EA=B3=84=20=EC=B6=9C=EB=A0=A5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../blackjack/controller/BlackjackController.java | 9 +++++++++ src/main/java/blackjack/model/CardStatus.java | 6 ------ src/main/java/blackjack/view/OutputView.java | 13 +++++++++++++ 3 files changed, 22 insertions(+), 6 deletions(-) diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index b64a4259eaf..12aab44b7af 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -4,9 +4,11 @@ import blackjack.model.CardProvider; import blackjack.model.Dealer; import blackjack.model.Player; +import blackjack.model.User; import blackjack.util.PlayerParser; import blackjack.view.InputView; import blackjack.view.OutputView; +import java.util.ArrayList; import java.util.List; @@ -30,6 +32,13 @@ public void run() { OutputView.printInitCards(players, dealer); hit(players, dealer); + + List users = new ArrayList<>(players); + users.addFirst(dealer); + + for (User user : users) { + OutputView.printCardStatus(user, cardCalculator.totalScore(user.getCardStatus().getCards())); + } } public void hit(List players, Dealer dealer) { diff --git a/src/main/java/blackjack/model/CardStatus.java b/src/main/java/blackjack/model/CardStatus.java index a90cfe39c4e..ad8e5f7683d 100644 --- a/src/main/java/blackjack/model/CardStatus.java +++ b/src/main/java/blackjack/model/CardStatus.java @@ -6,12 +6,10 @@ public class CardStatus { private final List cards; - private int totalScore; private boolean blackjack; public CardStatus() { this.cards = new ArrayList<>(); - this.totalScore = 0; this.blackjack = false; } @@ -19,10 +17,6 @@ public List getCards() { return cards; } - public int getTotalScore() { - return totalScore; - } - public boolean isBlackjack() { return blackjack; } diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index 13d2fa9ae3a..887a2dc2d9d 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -3,6 +3,7 @@ import blackjack.model.Card; import blackjack.model.Dealer; import blackjack.model.Player; +import blackjack.model.User; import java.util.List; public class OutputView { @@ -41,4 +42,16 @@ public static void printCantAddCard() { public static void printDealerHit() { System.out.println("딜러는 16이하라 한장의 카드를 더 받았습니다."); } + + public static void printCardStatus(User user, int totalScore) { + StringBuilder sb = new StringBuilder(); + + sb.append(user.getName() + "카드: "); + List cardFormats = user.getCardStatus().getCards().stream().map(Card::getFormat).toList(); + sb.append(String.join(", ", cardFormats)); + sb.append(" - 결과: " + totalScore).append("\n"); + + System.out.println(sb); + } + } From 9e9bff05b547371a85b42ab01d0ad98dfdaffd08 Mon Sep 17 00:00:00 2001 From: khyej Date: Thu, 5 Mar 2026 21:38:49 +0900 Subject: [PATCH 13/81] =?UTF-8?q?feat:=20=EC=B5=9C=EC=A2=85=20=EC=8A=B9?= =?UTF-8?q?=ED=8C=A8=20=EA=B3=84=EC=82=B0=20=EB=B0=8F=20=EC=B6=9C=EB=A0=A5?= =?UTF-8?q?=20=EA=B8=B0=EB=8A=A5=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/Application.java | 20 ++++++++ .../controller/BlackjackController.java | 16 ++++++- src/main/java/blackjack/model/Dealer.java | 4 ++ src/main/java/blackjack/model/GameResult.java | 6 ++- .../blackjack/model/GameResultCalculator.java | 47 +++++++++++++++++++ .../java/blackjack/model/GameSummary.java | 5 ++ src/main/java/blackjack/model/Player.java | 4 ++ src/main/java/blackjack/view/OutputView.java | 30 ++++++++++-- 8 files changed, 126 insertions(+), 6 deletions(-) create mode 100644 src/main/java/blackjack/model/GameResultCalculator.java create mode 100644 src/main/java/blackjack/model/GameSummary.java diff --git a/src/main/java/blackjack/Application.java b/src/main/java/blackjack/Application.java index a5767526aa7..f0fc6323220 100644 --- a/src/main/java/blackjack/Application.java +++ b/src/main/java/blackjack/Application.java @@ -1,4 +1,24 @@ package blackjack; +import blackjack.controller.BlackjackController; +import blackjack.model.CardCalculator; +import blackjack.model.CardProvider; +import blackjack.model.GameResultCalculator; + public class Application { + public static void main(String[] args) { + try { + CardProvider cardProvider = new CardProvider(); + CardCalculator cardCalculator = new CardCalculator(); + GameResultCalculator gameResultCalculator = new GameResultCalculator(); + BlackjackController blackjackController = new BlackjackController(cardProvider, cardCalculator, + gameResultCalculator); + blackjackController.run(); + + } catch (Exception e) { + // 오류 메시지 출력 + } finally { + + } + } } diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index 12aab44b7af..1a167096afd 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -3,6 +3,8 @@ import blackjack.model.CardCalculator; import blackjack.model.CardProvider; import blackjack.model.Dealer; +import blackjack.model.GameResultCalculator; +import blackjack.model.GameSummary; import blackjack.model.Player; import blackjack.model.User; import blackjack.util.PlayerParser; @@ -16,10 +18,13 @@ public class BlackjackController { private final CardProvider cardProvider; private final CardCalculator cardCalculator; + private final GameResultCalculator gameResultCalculator; - public BlackjackController(CardProvider cardProvider, CardCalculator cardCalculator) { + public BlackjackController(CardProvider cardProvider, CardCalculator cardCalculator, + GameResultCalculator gameResultCalculator) { this.cardProvider = cardProvider; this.cardCalculator = cardCalculator; + this.gameResultCalculator = gameResultCalculator; } public void run() { @@ -36,9 +41,16 @@ public void run() { List users = new ArrayList<>(players); users.addFirst(dealer); + List gameSummaries = new ArrayList<>(); for (User user : users) { - OutputView.printCardStatus(user, cardCalculator.totalScore(user.getCardStatus().getCards())); + GameSummary gameSummary = new GameSummary(user, cardCalculator.totalScore(user.getCardStatus().getCards())); + gameSummaries.add(gameSummary); + OutputView.printCardStatus(gameSummary); } + + gameResultCalculator.calculate(gameSummaries); + + OutputView.printGameResult(users); } public void hit(List players, Dealer dealer) { diff --git a/src/main/java/blackjack/model/Dealer.java b/src/main/java/blackjack/model/Dealer.java index 548eae94d20..7421f17aa9c 100644 --- a/src/main/java/blackjack/model/Dealer.java +++ b/src/main/java/blackjack/model/Dealer.java @@ -13,4 +13,8 @@ public Dealer() { public EnumMap getGameResults() { return gameResults; } + + public void addResult(GameResult gameResult) { + gameResults.put(gameResult, gameResults.getOrDefault(gameResult, 0) + 1); + } } diff --git a/src/main/java/blackjack/model/GameResult.java b/src/main/java/blackjack/model/GameResult.java index ec75683f550..b4dd6b86f20 100644 --- a/src/main/java/blackjack/model/GameResult.java +++ b/src/main/java/blackjack/model/GameResult.java @@ -12,4 +12,8 @@ public enum GameResult { GameResult(String format) { this.format = format; } -} + + public String getFormat() { + return format; + } +} \ No newline at end of file diff --git a/src/main/java/blackjack/model/GameResultCalculator.java b/src/main/java/blackjack/model/GameResultCalculator.java new file mode 100644 index 00000000000..df3c0ceff43 --- /dev/null +++ b/src/main/java/blackjack/model/GameResultCalculator.java @@ -0,0 +1,47 @@ +package blackjack.model; + +import java.util.List; + +public class GameResultCalculator { + + public void calculate(List gameSummaries) { + GameSummary dealerGameSummary = gameSummaries.getFirst(); + Dealer dealer = (Dealer) dealerGameSummary.user(); + int dealerTotalScore = dealerGameSummary.totalScore(); + List playerGameSummaries = gameSummaries.subList(1, gameSummaries.size()); + + for (GameSummary playerGameSummary : playerGameSummaries) { + Player player = (Player) playerGameSummary.user(); + int playerTotalScore = playerGameSummary.totalScore(); + if (playerTotalScore > 21) { + player.mark(GameResult.LOSE); + dealer.addResult(GameResult.WIN); + continue; + } + + if (dealerTotalScore > 21) { + dealer.addResult(GameResult.LOSE); + player.mark(GameResult.WIN); + continue; + } + + if (dealerTotalScore > playerTotalScore) { + dealer.addResult(GameResult.WIN); + player.mark(GameResult.LOSE); + continue; + } + + if (dealerTotalScore < playerTotalScore) { + dealer.addResult(GameResult.LOSE); + player.mark(GameResult.WIN); + continue; + } + + if (dealerTotalScore == playerTotalScore) { + dealer.addResult(GameResult.DRAW); + } + } + + + } +} diff --git a/src/main/java/blackjack/model/GameSummary.java b/src/main/java/blackjack/model/GameSummary.java new file mode 100644 index 00000000000..a762c49cbc7 --- /dev/null +++ b/src/main/java/blackjack/model/GameSummary.java @@ -0,0 +1,5 @@ +package blackjack.model; + +public record GameSummary(User user, int totalScore) { + +} diff --git a/src/main/java/blackjack/model/Player.java b/src/main/java/blackjack/model/Player.java index 2afb553035d..7bb937cc868 100644 --- a/src/main/java/blackjack/model/Player.java +++ b/src/main/java/blackjack/model/Player.java @@ -12,4 +12,8 @@ public Player(String name) { public GameResult getGameResult() { return gameResult; } + + public void mark(GameResult gameResult) { + this.gameResult = gameResult; + } } diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index 887a2dc2d9d..c49f2803509 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -2,8 +2,11 @@ import blackjack.model.Card; import blackjack.model.Dealer; +import blackjack.model.GameResult; +import blackjack.model.GameSummary; import blackjack.model.Player; import blackjack.model.User; +import java.util.EnumMap; import java.util.List; public class OutputView { @@ -43,15 +46,36 @@ public static void printDealerHit() { System.out.println("딜러는 16이하라 한장의 카드를 더 받았습니다."); } - public static void printCardStatus(User user, int totalScore) { - StringBuilder sb = new StringBuilder(); + public static void printCardStatus(GameSummary gameSummary) { + User user = gameSummary.user(); + StringBuilder sb = new StringBuilder(); sb.append(user.getName() + "카드: "); List cardFormats = user.getCardStatus().getCards().stream().map(Card::getFormat).toList(); sb.append(String.join(", ", cardFormats)); - sb.append(" - 결과: " + totalScore).append("\n"); + sb.append(" - 결과: " + gameSummary.totalScore()).append("\n"); System.out.println(sb); } + public static void printGameResult(List users) { + System.out.println("## 최종 승패"); + + Dealer dealer = (Dealer) users.getFirst(); + EnumMap dealerGameResult = dealer.getGameResults(); + System.out.println( + dealer.getName() + ": " + dealerGameResult.getOrDefault(GameResult.WIN, 0) + "승 " + + dealerGameResult.getOrDefault(GameResult.DRAW, 0) + "무 " + dealerGameResult.getOrDefault( + GameResult.LOSE, 0) + "패"); + + List players = users.stream() + .skip(1) + .map(user -> (Player) user) + .toList(); + for (Player player : players) { + System.out.print(player.getName() + ": "); + System.out.println(player.getGameResult().getFormat()); + } + } + } From 414c5b3c1cbb59fb4a9153ef20c592305bb2c904 Mon Sep 17 00:00:00 2001 From: khyej Date: Fri, 6 Mar 2026 16:49:25 +0900 Subject: [PATCH 14/81] =?UTF-8?q?feat:=20=EA=B2=8C=EC=9E=84=20=EC=8A=B9?= =?UTF-8?q?=ED=8C=A8=20=EA=B3=84=EC=82=B0=20=EB=A1=9C=EC=A7=81=20=EC=B6=94?= =?UTF-8?q?=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../controller/BlackjackController.java | 20 ++--- .../java/blackjack/model/CardCalculator.java | 13 ++- src/main/java/blackjack/model/CardStatus.java | 10 --- src/main/java/blackjack/model/Dealer.java | 2 +- .../blackjack/model/GameResultCalculator.java | 83 ++++++++++++++----- .../java/blackjack/model/GameSummary.java | 5 +- src/main/java/blackjack/model/User.java | 8 -- .../controller/BlackjackControllerTest.java | 26 +----- .../blackjack/model/CardCalculatorTest.java | 4 +- 9 files changed, 87 insertions(+), 84 deletions(-) diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index 1a167096afd..c40307aad9d 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -33,7 +33,6 @@ public void run() { Dealer dealer = new Dealer(); cardProvider.provideInitCards(players, dealer); - checkBlackjack(players, dealer); OutputView.printInitCards(players, dealer); hit(players, dealer); @@ -43,7 +42,11 @@ public void run() { List gameSummaries = new ArrayList<>(); for (User user : users) { - GameSummary gameSummary = new GameSummary(user, cardCalculator.totalScore(user.getCardStatus().getCards())); + int totalScore = cardCalculator.totalScore(user.getCardStatus().getCards()); + boolean bust = cardCalculator.calculateBust(totalScore); + boolean blackjack = cardCalculator.calculateBlackjack(user.getCardStatus().getCards()); + + GameSummary gameSummary = new GameSummary(user, totalScore, bust, blackjack); gameSummaries.add(gameSummary); OutputView.printCardStatus(gameSummary); } @@ -67,19 +70,6 @@ public void hit(List players, Dealer dealer) { } } - void checkBlackjack(List players, Dealer dealer) { - for (Player player : players) { - if (cardCalculator.totalScore(player.getCardStatus().getCards()) == 21) { - player.markBlackjack(); - } - } - - if (cardCalculator.totalScore(dealer.getCardStatus().getCards()) == 21) { - dealer.markBlackjack(); - } - } - - boolean checkAddCard(Player player) { if (cardCalculator.totalScore(player.getCardStatus().getCards()) >= 21) { OutputView.printCantAddCard(); diff --git a/src/main/java/blackjack/model/CardCalculator.java b/src/main/java/blackjack/model/CardCalculator.java index d2bf7f23fed..93049c0d7e1 100644 --- a/src/main/java/blackjack/model/CardCalculator.java +++ b/src/main/java/blackjack/model/CardCalculator.java @@ -6,6 +6,11 @@ public class CardCalculator { + public boolean calculateBlackjack(List cards) { + List initCards = cards.subList(0, 2); + return totalScore(initCards) == 21; + } + public int totalScore(List cards) { Map> partitioned = cards.stream() .collect(Collectors.partitioningBy(card -> @@ -21,10 +26,14 @@ public int totalScore(List cards) { .mapToInt(Card::getNumber) .sum(); - return getTotalScore(aceCards, totalScoreNonAce); + return addAceScore(aceCards, totalScoreNonAce); + } + + public boolean calculateBust(int totalScore) { + return totalScore > 21; } - int getTotalScore(List aceCards, int totalScore) { + int addAceScore(List aceCards, int totalScore) { for (int i = 0; i < aceCards.size(); i++) { if (totalScore + 11 > 21) { totalScore += 1; diff --git a/src/main/java/blackjack/model/CardStatus.java b/src/main/java/blackjack/model/CardStatus.java index ad8e5f7683d..64600107792 100644 --- a/src/main/java/blackjack/model/CardStatus.java +++ b/src/main/java/blackjack/model/CardStatus.java @@ -6,26 +6,16 @@ public class CardStatus { private final List cards; - private boolean blackjack; public CardStatus() { this.cards = new ArrayList<>(); - this.blackjack = false; } public List getCards() { return cards; } - public boolean isBlackjack() { - return blackjack; - } - public void addCard(Card card) { cards.add(card); } - - public void markBlackjack() { - this.blackjack = true; - } } diff --git a/src/main/java/blackjack/model/Dealer.java b/src/main/java/blackjack/model/Dealer.java index 7421f17aa9c..5bc061c9142 100644 --- a/src/main/java/blackjack/model/Dealer.java +++ b/src/main/java/blackjack/model/Dealer.java @@ -3,7 +3,7 @@ import java.util.EnumMap; public class Dealer extends User { - private EnumMap gameResults; + private final EnumMap gameResults; public Dealer() { super("딜러"); diff --git a/src/main/java/blackjack/model/GameResultCalculator.java b/src/main/java/blackjack/model/GameResultCalculator.java index df3c0ceff43..2790c4cac18 100644 --- a/src/main/java/blackjack/model/GameResultCalculator.java +++ b/src/main/java/blackjack/model/GameResultCalculator.java @@ -3,7 +3,6 @@ import java.util.List; public class GameResultCalculator { - public void calculate(List gameSummaries) { GameSummary dealerGameSummary = gameSummaries.getFirst(); Dealer dealer = (Dealer) dealerGameSummary.user(); @@ -13,35 +12,77 @@ public void calculate(List gameSummaries) { for (GameSummary playerGameSummary : playerGameSummaries) { Player player = (Player) playerGameSummary.user(); int playerTotalScore = playerGameSummary.totalScore(); - if (playerTotalScore > 21) { - player.mark(GameResult.LOSE); - dealer.addResult(GameResult.WIN); - continue; - } - if (dealerTotalScore > 21) { - dealer.addResult(GameResult.LOSE); - player.mark(GameResult.WIN); + if (calculateWhenBlackjack(playerGameSummary, dealerGameSummary, dealer, player)) { continue; } - if (dealerTotalScore > playerTotalScore) { - dealer.addResult(GameResult.WIN); - player.mark(GameResult.LOSE); + if (calculateWhenBust(playerGameSummary, dealerGameSummary, dealer, player)) { continue; } - if (dealerTotalScore < playerTotalScore) { - dealer.addResult(GameResult.LOSE); - player.mark(GameResult.WIN); - continue; - } + calculateWhenNormal(dealerTotalScore, playerTotalScore, dealer, player); + } + } - if (dealerTotalScore == playerTotalScore) { - dealer.addResult(GameResult.DRAW); - } + private static boolean calculateWhenBlackjack(GameSummary playerGameSummary, GameSummary dealerGameSummary, + Dealer dealer, + Player player) { + if (dealerGameSummary.blackjack() && playerGameSummary.blackjack()) { + dealer.addResult(GameResult.DRAW); + return true; + } + + if (playerGameSummary.blackjack()) { + player.mark(GameResult.WIN); + dealer.addResult(GameResult.LOSE); + return true; } + if (dealerGameSummary.blackjack()) { + player.mark(GameResult.LOSE); + dealer.addResult(GameResult.WIN); + return true; + } + return false; + } + + private static boolean calculateWhenBust(GameSummary playerGameSummary, GameSummary dealerGameSummary, + Dealer dealer, + Player player) { + if (playerGameSummary.bust() && dealerGameSummary.bust()) { + dealer.addResult(GameResult.WIN); + player.mark(GameResult.LOSE); + return true; + } + + if (playerGameSummary.bust()) { + player.mark(GameResult.LOSE); + dealer.addResult(GameResult.WIN); + return true; + } + + if (dealerGameSummary.bust()) { + dealer.addResult(GameResult.LOSE); + player.mark(GameResult.WIN); + return true; + } + return false; + } + + private static void calculateWhenNormal(int dealerTotalScore, int playerTotalScore, Dealer dealer, Player player) { + if (dealerTotalScore > playerTotalScore) { + dealer.addResult(GameResult.WIN); + player.mark(GameResult.LOSE); + return; + } + + if (dealerTotalScore < playerTotalScore) { + dealer.addResult(GameResult.LOSE); + player.mark(GameResult.WIN); + return; + } + dealer.addResult(GameResult.DRAW); } -} +} \ No newline at end of file diff --git a/src/main/java/blackjack/model/GameSummary.java b/src/main/java/blackjack/model/GameSummary.java index a762c49cbc7..5453fe3606f 100644 --- a/src/main/java/blackjack/model/GameSummary.java +++ b/src/main/java/blackjack/model/GameSummary.java @@ -1,5 +1,4 @@ package blackjack.model; -public record GameSummary(User user, int totalScore) { - -} +public record GameSummary(User user, int totalScore, boolean bust, boolean blackjack) { +} \ No newline at end of file diff --git a/src/main/java/blackjack/model/User.java b/src/main/java/blackjack/model/User.java index 4727a9332ab..964402dbe41 100644 --- a/src/main/java/blackjack/model/User.java +++ b/src/main/java/blackjack/model/User.java @@ -21,12 +21,4 @@ public CardStatus getCardStatus() { public void addCard(Card card) { cardStatus.addCard(card); } - - public void markBlackjack() { - cardStatus.markBlackjack(); - } - - public boolean isBlackjack() { - return cardStatus.isBlackjack(); - } } diff --git a/src/test/java/blackjack/controller/BlackjackControllerTest.java b/src/test/java/blackjack/controller/BlackjackControllerTest.java index 7b36a9c316d..de12bb63320 100644 --- a/src/test/java/blackjack/controller/BlackjackControllerTest.java +++ b/src/test/java/blackjack/controller/BlackjackControllerTest.java @@ -3,9 +3,8 @@ import blackjack.model.Card; import blackjack.model.CardCalculator; import blackjack.model.CardProvider; -import blackjack.model.Dealer; +import blackjack.model.GameResultCalculator; import blackjack.model.Player; -import java.util.List; import org.assertj.core.api.Assertions; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; @@ -13,26 +12,9 @@ class BlackjackControllerTest { private final CardProvider cardProvider = new CardProvider(); private final CardCalculator cardCalculator = new CardCalculator(); - private final BlackjackController blackjackController = new BlackjackController(cardProvider, cardCalculator); - - @Test - @DisplayName("최초 배분 카드 두 장의 합이 21일 경우 블랙잭") - void test_checkBlackjack() { - Player player = new Player("pobi"); - List players = List.of(player); - Dealer dealer = new Dealer(); - - player.addCard(Card.A_CLOVER); - player.addCard(Card.J_DIA); - - dealer.addCard(Card.A_CLOVER); - dealer.addCard(Card.J_DIA); - - blackjackController.checkBlackjack(players, dealer); - - Assertions.assertThat(player.isBlackjack()).isTrue(); - Assertions.assertThat(dealer.isBlackjack()).isTrue(); - } + private final GameResultCalculator gameResultCalculator = new GameResultCalculator(); + private final BlackjackController blackjackController = new BlackjackController(cardProvider, cardCalculator, + gameResultCalculator); @Test diff --git a/src/test/java/blackjack/model/CardCalculatorTest.java b/src/test/java/blackjack/model/CardCalculatorTest.java index b02185fd063..fff6f9048d9 100644 --- a/src/test/java/blackjack/model/CardCalculatorTest.java +++ b/src/test/java/blackjack/model/CardCalculatorTest.java @@ -14,7 +14,7 @@ void test_getTotalScore_when_ace_is_eleven() { int totalScore = 10; CardCalculator cardCalculator = new CardCalculator(); - int result = cardCalculator.getTotalScore(aceCards, totalScore); + int result = cardCalculator.addAceScore(aceCards, totalScore); Assertions.assertThat(result).isEqualTo(totalScore + 11); } @@ -26,7 +26,7 @@ void test_getTotalScore_when_ace_is_one() { int totalScore = 11; CardCalculator cardCalculator = new CardCalculator(); - int result = cardCalculator.getTotalScore(aceCards, totalScore); + int result = cardCalculator.addAceScore(aceCards, totalScore); Assertions.assertThat(result).isEqualTo(totalScore + 1); } From 18f2d9c1a6a3947ed12bbb6c4718bdb0a8e9aff5 Mon Sep 17 00:00:00 2001 From: khyej Date: Fri, 6 Mar 2026 17:02:30 +0900 Subject: [PATCH 15/81] =?UTF-8?q?refactor:=20=EC=B6=9C=EB=A0=A5=EB=AC=B8?= =?UTF-8?q?=20=ED=98=95=EC=8B=9D=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/view/OutputView.java | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index c49f2803509..f21dbe83cbe 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -15,6 +15,7 @@ public static void printInitCards(List players, Dealer dealer) { .map(Player::getName) .toList(); StringBuilder sb = new StringBuilder(); + sb.append("\n"); sb.append("딜러와 "); sb.append(String.join(", ", names)); sb.append("에게 2장을 나누었습니다."); @@ -24,6 +25,7 @@ public static void printInitCards(List players, Dealer dealer) { for (Player player : players) { printPlayerCards(player); } + System.out.println(); } private static void printDealerCard(Dealer dealer) { @@ -43,7 +45,7 @@ public static void printCantAddCard() { } public static void printDealerHit() { - System.out.println("딜러는 16이하라 한장의 카드를 더 받았습니다."); + System.out.println("\n딜러는 16이하라 한장의 카드를 더 받았습니다.\n"); } public static void printCardStatus(GameSummary gameSummary) { @@ -53,12 +55,13 @@ public static void printCardStatus(GameSummary gameSummary) { sb.append(user.getName() + "카드: "); List cardFormats = user.getCardStatus().getCards().stream().map(Card::getFormat).toList(); sb.append(String.join(", ", cardFormats)); - sb.append(" - 결과: " + gameSummary.totalScore()).append("\n"); + sb.append(" - 결과: " + gameSummary.totalScore()); System.out.println(sb); } public static void printGameResult(List users) { + System.out.println(); System.out.println("## 최종 승패"); Dealer dealer = (Dealer) users.getFirst(); From f58565d177cf3342b3486a018bf553901967ea7c Mon Sep 17 00:00:00 2001 From: khyej Date: Fri, 6 Mar 2026 17:48:03 +0900 Subject: [PATCH 16/81] =?UTF-8?q?feat:=20=EC=98=88=EC=99=B8=20=EC=B2=98?= =?UTF-8?q?=EB=A6=AC=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/Application.java | 2 +- .../controller/BlackjackController.java | 19 +++++++++++++++--- .../java/blackjack/model/ErrorMessage.java | 19 ++++++++++++++++++ .../java/blackjack/util/ExceptionHandler.java | 17 ++++++++++++++++ .../java/blackjack/util/PlayerParser.java | 20 ++++++------------- src/main/java/blackjack/util/Validator.java | 20 +++++++++++++++++++ src/main/java/blackjack/view/OutputView.java | 4 ++++ 7 files changed, 83 insertions(+), 18 deletions(-) create mode 100644 src/main/java/blackjack/model/ErrorMessage.java create mode 100644 src/main/java/blackjack/util/ExceptionHandler.java create mode 100644 src/main/java/blackjack/util/Validator.java diff --git a/src/main/java/blackjack/Application.java b/src/main/java/blackjack/Application.java index f0fc6323220..c9ca234c860 100644 --- a/src/main/java/blackjack/Application.java +++ b/src/main/java/blackjack/Application.java @@ -16,7 +16,7 @@ public static void main(String[] args) { blackjackController.run(); } catch (Exception e) { - // 오류 메시지 출력 + } finally { } diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index c40307aad9d..a4ad4c4715e 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -1,13 +1,17 @@ package blackjack.controller; +import static blackjack.util.ExceptionHandler.retryUntilSuccess; + import blackjack.model.CardCalculator; import blackjack.model.CardProvider; import blackjack.model.Dealer; +import blackjack.model.ErrorMessage; import blackjack.model.GameResultCalculator; import blackjack.model.GameSummary; import blackjack.model.Player; import blackjack.model.User; import blackjack.util.PlayerParser; +import blackjack.util.Validator; import blackjack.view.InputView; import blackjack.view.OutputView; import java.util.ArrayList; @@ -28,8 +32,10 @@ public BlackjackController(CardProvider cardProvider, CardCalculator cardCalcula } public void run() { - String input = InputView.readPlayerName(); - List players = PlayerParser.parse(input); + List players = retryUntilSuccess(() -> { + String input = InputView.readPlayerName(); + return PlayerParser.parse(input); + }); Dealer dealer = new Dealer(); cardProvider.provideInitCards(players, dealer); @@ -58,7 +64,7 @@ public void run() { public void hit(List players, Dealer dealer) { for (Player player : players) { - while (InputView.readCardAdd(player).equals("y") && checkAddCard(player)) { + while (retryUntilSuccess(() -> checkY(player)) && checkAddCard(player)) { cardProvider.provideOneCard(player); OutputView.printPlayerCards(player); } @@ -70,6 +76,13 @@ public void hit(List players, Dealer dealer) { } } + private static boolean checkY(Player player) { + String input = InputView.readCardAdd(player).trim(); + Validator.validateEmpty(input, ErrorMessage.ERROR_EMPTY_INPUT.getErrorMessage()); + Validator.validateRegrex("^[yYnN]$", input, ErrorMessage.ERROR_NOT_Y_N_INPUT.getErrorMessage()); + return input.equals("y"); + } + boolean checkAddCard(Player player) { if (cardCalculator.totalScore(player.getCardStatus().getCards()) >= 21) { OutputView.printCantAddCard(); diff --git a/src/main/java/blackjack/model/ErrorMessage.java b/src/main/java/blackjack/model/ErrorMessage.java new file mode 100644 index 00000000000..07edd5b5ce0 --- /dev/null +++ b/src/main/java/blackjack/model/ErrorMessage.java @@ -0,0 +1,19 @@ +package blackjack.model; + +public enum ErrorMessage { + + ERROR_EMPTY_INPUT("입력값은 공백일 수 없습니다."), + ERROR_NOT_Y_N_INPUT("입력값은 y 또는 n만 가능합니다."), + ERROR_INVALID_PLAYER_NAME("플레이어의 이름은 영어 or 한글로만 이루어질 수 있습니다."), + ; + + private final String errorMessage; + + ErrorMessage(String errorMessage) { + this.errorMessage = errorMessage; + } + + public String getErrorMessage() { + return errorMessage; + } +} diff --git a/src/main/java/blackjack/util/ExceptionHandler.java b/src/main/java/blackjack/util/ExceptionHandler.java new file mode 100644 index 00000000000..0df9a672376 --- /dev/null +++ b/src/main/java/blackjack/util/ExceptionHandler.java @@ -0,0 +1,17 @@ +package blackjack.util; + +import blackjack.view.OutputView; +import java.util.function.Supplier; + +public class ExceptionHandler { + + public static T retryUntilSuccess(Supplier supplier) { + while (true) { + try { + return supplier.get(); + } catch (IllegalArgumentException e) { + OutputView.printError(e.getMessage()); + } + } + } +} diff --git a/src/main/java/blackjack/util/PlayerParser.java b/src/main/java/blackjack/util/PlayerParser.java index 0150bab270c..6e12c0167b7 100644 --- a/src/main/java/blackjack/util/PlayerParser.java +++ b/src/main/java/blackjack/util/PlayerParser.java @@ -1,9 +1,11 @@ package blackjack.util; +import static blackjack.model.ErrorMessage.ERROR_EMPTY_INPUT; +import static blackjack.model.ErrorMessage.ERROR_INVALID_PLAYER_NAME; + import blackjack.model.Player; import java.util.Arrays; import java.util.List; -import java.util.regex.Pattern; public class PlayerParser { @@ -12,21 +14,11 @@ public class PlayerParser { public static List parse(String names) { return Arrays.stream(names.split(",")) .map(String::trim) - .peek(PlayerParser::validateRegrex) - .peek(PlayerParser::validateEmpty) + .peek((name) -> Validator.validateRegrex(regrex, name, + ERROR_INVALID_PLAYER_NAME.getErrorMessage())) + .peek((name) -> Validator.validateEmpty(name, ERROR_EMPTY_INPUT.getErrorMessage())) .map(Player::new) .toList(); } - private static void validateRegrex(String parsedName) { - if (!Pattern.matches(regrex, parsedName)) { - throw new IllegalArgumentException("플레이어의 이름은 영어 or 한글로만 이루어질 수 있습니다."); - } - } - - private static void validateEmpty(String parsedName) { - if (parsedName.isEmpty()) { - throw new IllegalArgumentException("플레이어의 이름은 공백일 수 없습니다."); - } - } } diff --git a/src/main/java/blackjack/util/Validator.java b/src/main/java/blackjack/util/Validator.java new file mode 100644 index 00000000000..0a657231a3d --- /dev/null +++ b/src/main/java/blackjack/util/Validator.java @@ -0,0 +1,20 @@ +package blackjack.util; + +import static blackjack.model.ErrorMessage.ERROR_EMPTY_INPUT; + +import java.util.regex.Pattern; + +public class Validator { + + public static void validateRegrex(String regrex, String input, String errorMessage) { + if (!Pattern.matches(regrex, input)) { + throw new IllegalArgumentException(errorMessage); + } + } + + public static void validateEmpty(String input, String errorMessage) { + if (input.isEmpty()) { + throw new IllegalArgumentException(ERROR_EMPTY_INPUT.getErrorMessage()); + } + } +} diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index f21dbe83cbe..d7cdd3ac5ce 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -81,4 +81,8 @@ public static void printGameResult(List users) { } } + public static void printError(String errorMessage) { + System.out.println("[ERROR] " + errorMessage); + } + } From a2b6b06391ed121686a426221c46d765ce7418ee Mon Sep 17 00:00:00 2001 From: khyej Date: Fri, 6 Mar 2026 18:20:15 +0900 Subject: [PATCH 17/81] =?UTF-8?q?refactor:=20getter=20=EC=A0=9C=EA=B1=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/Application.java | 17 ++++------ .../controller/BlackjackController.java | 34 +++++++++++++------ src/main/java/blackjack/model/User.java | 6 ++-- src/main/java/blackjack/view/OutputView.java | 6 ++-- .../blackjack/model/CardProviderTest.java | 6 ++-- 5 files changed, 40 insertions(+), 29 deletions(-) diff --git a/src/main/java/blackjack/Application.java b/src/main/java/blackjack/Application.java index c9ca234c860..2a8f8fde75c 100644 --- a/src/main/java/blackjack/Application.java +++ b/src/main/java/blackjack/Application.java @@ -7,18 +7,13 @@ public class Application { public static void main(String[] args) { - try { - CardProvider cardProvider = new CardProvider(); - CardCalculator cardCalculator = new CardCalculator(); - GameResultCalculator gameResultCalculator = new GameResultCalculator(); - BlackjackController blackjackController = new BlackjackController(cardProvider, cardCalculator, - gameResultCalculator); - blackjackController.run(); - } catch (Exception e) { - - } finally { + CardProvider cardProvider = new CardProvider(); + CardCalculator cardCalculator = new CardCalculator(); + GameResultCalculator gameResultCalculator = new GameResultCalculator(); + BlackjackController blackjackController = new BlackjackController(cardProvider, cardCalculator, + gameResultCalculator); + blackjackController.run(); - } } } diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index a4ad4c4715e..b7459e21362 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -38,28 +38,42 @@ public void run() { }); Dealer dealer = new Dealer(); - cardProvider.provideInitCards(players, dealer); - OutputView.printInitCards(players, dealer); + provideInitCardsPrint(players, dealer); hit(players, dealer); List users = new ArrayList<>(players); users.addFirst(dealer); + List gameSummaries = createGameSummaryAndPrint(users); + + createGameResultAndPrint(gameSummaries, users); + + InputView.closeScanner(); + } + + private void provideInitCardsPrint(List players, Dealer dealer) { + cardProvider.provideInitCards(players, dealer); + OutputView.printInitCards(players, dealer); + } + + private void createGameResultAndPrint(List gameSummaries, List users) { + gameResultCalculator.calculate(gameSummaries); + OutputView.printGameResult(users); + } + + private List createGameSummaryAndPrint(List users) { List gameSummaries = new ArrayList<>(); for (User user : users) { - int totalScore = cardCalculator.totalScore(user.getCardStatus().getCards()); + int totalScore = cardCalculator.totalScore(user.cards()); boolean bust = cardCalculator.calculateBust(totalScore); - boolean blackjack = cardCalculator.calculateBlackjack(user.getCardStatus().getCards()); + boolean blackjack = cardCalculator.calculateBlackjack(user.cards()); GameSummary gameSummary = new GameSummary(user, totalScore, bust, blackjack); gameSummaries.add(gameSummary); OutputView.printCardStatus(gameSummary); } - - gameResultCalculator.calculate(gameSummaries); - - OutputView.printGameResult(users); + return gameSummaries; } public void hit(List players, Dealer dealer) { @@ -70,7 +84,7 @@ public void hit(List players, Dealer dealer) { } } - while (cardCalculator.totalScore(dealer.getCardStatus().getCards()) < 17) { + while (cardCalculator.totalScore(dealer.cards()) < 17) { OutputView.printDealerHit(); cardProvider.provideOneCard(dealer); } @@ -84,7 +98,7 @@ private static boolean checkY(Player player) { } boolean checkAddCard(Player player) { - if (cardCalculator.totalScore(player.getCardStatus().getCards()) >= 21) { + if (cardCalculator.totalScore(player.cards()) >= 21) { OutputView.printCantAddCard(); return false; } diff --git a/src/main/java/blackjack/model/User.java b/src/main/java/blackjack/model/User.java index 964402dbe41..8e4bc795ed3 100644 --- a/src/main/java/blackjack/model/User.java +++ b/src/main/java/blackjack/model/User.java @@ -1,5 +1,7 @@ package blackjack.model; +import java.util.List; + public class User { private final String name; @@ -14,8 +16,8 @@ public String getName() { return name; } - public CardStatus getCardStatus() { - return cardStatus; + public List cards() { + return cardStatus.getCards(); } public void addCard(Card card) { diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index d7cdd3ac5ce..2a07fdbbf1f 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -29,11 +29,11 @@ public static void printInitCards(List players, Dealer dealer) { } private static void printDealerCard(Dealer dealer) { - System.out.println("딜러카드: " + dealer.getCardStatus().getCards().getFirst().getFormat()); + System.out.println("딜러카드: " + dealer.cards().getFirst().getFormat()); } public static void printPlayerCards(Player player) { - List formats = player.getCardStatus().getCards().stream() + List formats = player.cards().stream() .map(Card::getFormat) .toList(); @@ -53,7 +53,7 @@ public static void printCardStatus(GameSummary gameSummary) { StringBuilder sb = new StringBuilder(); sb.append(user.getName() + "카드: "); - List cardFormats = user.getCardStatus().getCards().stream().map(Card::getFormat).toList(); + List cardFormats = user.cards().stream().map(Card::getFormat).toList(); sb.append(String.join(", ", cardFormats)); sb.append(" - 결과: " + gameSummary.totalScore()); diff --git a/src/test/java/blackjack/model/CardProviderTest.java b/src/test/java/blackjack/model/CardProviderTest.java index 6035188f9aa..e9f6a2da23f 100644 --- a/src/test/java/blackjack/model/CardProviderTest.java +++ b/src/test/java/blackjack/model/CardProviderTest.java @@ -19,9 +19,9 @@ void test_provide_init_cards() { cardProvider.provideInitCards(players, dealer); for (Player player : players) { - assertThat(player.getCardStatus().getCards().size()).isEqualTo(2); + assertThat(player.cards().size()).isEqualTo(2); } - assertThat(dealer.getCardStatus().getCards().size()).isEqualTo(2); + assertThat(dealer.cards().size()).isEqualTo(2); } @Test @@ -32,7 +32,7 @@ void test_provide_one_card_success() { cardProvider.provideOneCard(player); - assertThat(player.getCardStatus().getCards().size()).isEqualTo(1); + assertThat(player.cards().size()).isEqualTo(1); } } \ No newline at end of file From d855fc46b4c1df2565669af3cc8229bbe59280d7 Mon Sep 17 00:00:00 2001 From: khyej Date: Fri, 6 Mar 2026 18:38:06 +0900 Subject: [PATCH 18/81] =?UTF-8?q?refactor:=20=EB=A7=A4=EC=A7=81=EB=B3=80?= =?UTF-8?q?=EC=88=98=20=EC=83=81=EC=88=98=ED=99=94?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../controller/BlackjackController.java | 10 +++++++--- .../java/blackjack/model/CardCalculator.java | 18 ++++++++++++------ .../java/blackjack/model/CardProvider.java | 5 ++++- src/main/java/blackjack/model/Constant.java | 14 ++++++++++++++ src/main/java/blackjack/util/PlayerParser.java | 4 ++-- src/main/java/blackjack/view/OutputView.java | 4 +++- 6 files changed, 42 insertions(+), 13 deletions(-) create mode 100644 src/main/java/blackjack/model/Constant.java diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index b7459e21362..f3e45c88d89 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -1,5 +1,7 @@ package blackjack.controller; +import static blackjack.model.Constant.DEALER_ADD_CARD_STAND; +import static blackjack.model.Constant.TWENTY_ONE; import static blackjack.util.ExceptionHandler.retryUntilSuccess; import blackjack.model.CardCalculator; @@ -20,6 +22,8 @@ public class BlackjackController { + private static final String Y_N_REGREX = "^[yYnN]$"; + private final CardProvider cardProvider; private final CardCalculator cardCalculator; private final GameResultCalculator gameResultCalculator; @@ -84,7 +88,7 @@ public void hit(List players, Dealer dealer) { } } - while (cardCalculator.totalScore(dealer.cards()) < 17) { + while (cardCalculator.totalScore(dealer.cards()) < DEALER_ADD_CARD_STAND) { OutputView.printDealerHit(); cardProvider.provideOneCard(dealer); } @@ -93,12 +97,12 @@ public void hit(List players, Dealer dealer) { private static boolean checkY(Player player) { String input = InputView.readCardAdd(player).trim(); Validator.validateEmpty(input, ErrorMessage.ERROR_EMPTY_INPUT.getErrorMessage()); - Validator.validateRegrex("^[yYnN]$", input, ErrorMessage.ERROR_NOT_Y_N_INPUT.getErrorMessage()); + Validator.validateRegrex(Y_N_REGREX, input, ErrorMessage.ERROR_NOT_Y_N_INPUT.getErrorMessage()); return input.equals("y"); } boolean checkAddCard(Player player) { - if (cardCalculator.totalScore(player.cards()) >= 21) { + if (cardCalculator.totalScore(player.cards()) >= TWENTY_ONE) { OutputView.printCantAddCard(); return false; } diff --git a/src/main/java/blackjack/model/CardCalculator.java b/src/main/java/blackjack/model/CardCalculator.java index 93049c0d7e1..8a6da8dde50 100644 --- a/src/main/java/blackjack/model/CardCalculator.java +++ b/src/main/java/blackjack/model/CardCalculator.java @@ -1,5 +1,11 @@ package blackjack.model; +import static blackjack.model.Constant.ACE_SCORE_ELEVEN; +import static blackjack.model.Constant.ACE_SCORE_ONE; +import static blackjack.model.Constant.INIT_CARDS_END_IDX; +import static blackjack.model.Constant.INIT_CARDS_START_IDX; +import static blackjack.model.Constant.TWENTY_ONE; + import java.util.List; import java.util.Map; import java.util.stream.Collectors; @@ -7,8 +13,8 @@ public class CardCalculator { public boolean calculateBlackjack(List cards) { - List initCards = cards.subList(0, 2); - return totalScore(initCards) == 21; + List initCards = cards.subList(INIT_CARDS_START_IDX, INIT_CARDS_END_IDX); + return totalScore(initCards) == TWENTY_ONE; } public int totalScore(List cards) { @@ -30,16 +36,16 @@ public int totalScore(List cards) { } public boolean calculateBust(int totalScore) { - return totalScore > 21; + return totalScore > TWENTY_ONE; } int addAceScore(List aceCards, int totalScore) { for (int i = 0; i < aceCards.size(); i++) { - if (totalScore + 11 > 21) { - totalScore += 1; + if (totalScore + ACE_SCORE_ELEVEN > TWENTY_ONE) { + totalScore += ACE_SCORE_ONE; continue; } - totalScore += 11; + totalScore += ACE_SCORE_ELEVEN; } return totalScore; diff --git a/src/main/java/blackjack/model/CardProvider.java b/src/main/java/blackjack/model/CardProvider.java index 4bc119b5a32..141da1f2ded 100644 --- a/src/main/java/blackjack/model/CardProvider.java +++ b/src/main/java/blackjack/model/CardProvider.java @@ -1,5 +1,8 @@ package blackjack.model; +import static blackjack.model.Constant.INIT_CARDS_END_IDX; +import static blackjack.model.Constant.INIT_CARDS_START_IDX; + import java.util.ArrayList; import java.util.Collections; import java.util.LinkedList; @@ -23,7 +26,7 @@ private void initDeck() { } public void provideInitCards(List players, Dealer dealer) { - for (int i = 0; i < 2; i++) { + for (int i = INIT_CARDS_START_IDX; i < INIT_CARDS_END_IDX; i++) { for (Player player : players) { player.addCard(deck.poll()); } diff --git a/src/main/java/blackjack/model/Constant.java b/src/main/java/blackjack/model/Constant.java new file mode 100644 index 00000000000..233e45e55d4 --- /dev/null +++ b/src/main/java/blackjack/model/Constant.java @@ -0,0 +1,14 @@ +package blackjack.model; + +public class Constant { + + public static final int DEALER_ADD_CARD_STAND = 17; + public static final int TWENTY_ONE = 21; + + public static final int INIT_CARDS_START_IDX = 0; + public static final int INIT_CARDS_END_IDX = 2; + + public static final int ACE_SCORE_ONE = 1; + public static final int ACE_SCORE_ELEVEN = 11; + +} diff --git a/src/main/java/blackjack/util/PlayerParser.java b/src/main/java/blackjack/util/PlayerParser.java index 6e12c0167b7..55f41fe392c 100644 --- a/src/main/java/blackjack/util/PlayerParser.java +++ b/src/main/java/blackjack/util/PlayerParser.java @@ -9,12 +9,12 @@ public class PlayerParser { - private static final String regrex = "^[a-zA-Z가-힣]*$"; + private static final String PLAYER_NAME_REGREX = "^[a-zA-Z가-힣]*$"; public static List parse(String names) { return Arrays.stream(names.split(",")) .map(String::trim) - .peek((name) -> Validator.validateRegrex(regrex, name, + .peek((name) -> Validator.validateRegrex(PLAYER_NAME_REGREX, name, ERROR_INVALID_PLAYER_NAME.getErrorMessage())) .peek((name) -> Validator.validateEmpty(name, ERROR_EMPTY_INPUT.getErrorMessage())) .map(Player::new) diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index 2a07fdbbf1f..08b75bdd219 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -1,5 +1,7 @@ package blackjack.view; +import static blackjack.model.Constant.TWENTY_ONE; + import blackjack.model.Card; import blackjack.model.Dealer; import blackjack.model.GameResult; @@ -41,7 +43,7 @@ public static void printPlayerCards(Player player) { } public static void printCantAddCard() { - System.out.println("카드의 합계가 21 이상입니다. 더이상 카드를 받을 수 없습니다."); + System.out.println("카드의 합계가 " + TWENTY_ONE + " 이상입니다. 더이상 카드를 받을 수 없습니다."); } public static void printDealerHit() { From 46807d6d63db681797a4ea5028cecdb2b8eb3351 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Fri, 6 Mar 2026 19:07:03 +0900 Subject: [PATCH 19/81] =?UTF-8?q?docs:=20=EA=B5=AC=ED=98=84=20=EA=B8=B0?= =?UTF-8?q?=EB=8A=A5=20=EB=AA=A9=EB=A1=9D=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 38 +++++++++++++++++++++++++++----------- 1 file changed, 27 insertions(+), 11 deletions(-) diff --git a/README.md b/README.md index 75f79f000e9..cc23089b189 100644 --- a/README.md +++ b/README.md @@ -5,22 +5,38 @@ --- ### 구현 기능 목록 - -1. [입력] 게임에 참여할 사람의 이름을 입력 받는다.(쉼표 기준으로 분리) +**1. [입력] 게임에 참여할 사람의 이름을 입력 받는다.(쉼표 기준으로 분리)** + [예외처리] 쉼표 외의 다른 문자를 구분자로 한 경우 IllegalArgumentException 예외를 발생시킨다. + [예외처리] 입력값이 공백일 경우 IllegalArgumentException 예외를 발생시킨다. -2. [중간 과정] 딜러와 사용자에게 카드를 2장씩 나누어준다. + +**2. [중간 과정] 딜러와 사용자에게 카드를 2장씩 나누어준다.** + [카드 조건] 덱은 1개만 사용한다.(A ~ K : 13 * 4 = 52장) -3. [중간 과정] 딜러와 사용자의 최초 카드 합계를 구하며, 블랙잭 여부를 판단한다. + +**3. [중간 과정] 딜러와 사용자의 최초 카드 합계를 구하며, 블랙잭 여부를 판단한다.** + [ACE 조건] ACE가 11이어도 21이 넘지 않는 경우에는 11, 넘는 경우에는 1로 계산한다. -4. [출력] 카드 현황을 출력한다. + +**4. [출력] 카드 현황을 출력한다.** + [출력 조건] 딜러는 첫 번째 카드만 출력한다. -5. [입력] 사용자별로 카드 추가 지급 여부를 입력 받는다. + +**5. [입력] 사용자별로 카드 추가 지급 여부를 입력 받는다.** + [예외처리] y, n 외의 다른 문자일 경우 IllegalArgumentException 예외를 발생시킨다. + [입력 조건] 모든 사용자가 추가 지급을 완료할 때까지 반복한다. + [지급 조건] 사용자가 y를 입력하고, 사용자의 현재 카드 합계가 21미만일 경우에 카드를 지급한다. -6. [출력] 사용자별로 지급 현황을 출력한다. -7. [출력] 딜러의 카드 합계가 17 이상이 일 될 때까지 추가 지급 현황을 출력한다. -8. [출력] 사용자별 카드 현황 및 결과를 출력한다. -9. [중간 과정] 최종 승패 여부를 계산한다. -10. [출력] 최종 승패를 출력한다. + +**6. [출력] 사용자별로 지급 현황을 출력한다.** + +**7. [출력] 딜러의 카드 합계가 17 이상이 일 될 때까지 추가 지급 현황을 출력한다.** + +**8. [출력] 사용자별 카드 현황 및 결과를 출력한다.** + +**9. [중간 과정] 최종 승패 여부를 계산한다.** + +**10. [출력] 최종 승패를 출력한다.** From e97ce9b6178fe42e330c441b243ef06d762dc59a Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Sun, 8 Mar 2026 14:29:13 +0900 Subject: [PATCH 20/81] =?UTF-8?q?test:=20DisplayName=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/{CardStatus.java => Hand.java} | 0 src/test/java/blackjack/controller/BlackjackControllerTest.java | 2 +- 2 files changed, 1 insertion(+), 1 deletion(-) rename src/main/java/blackjack/model/{CardStatus.java => Hand.java} (100%) diff --git a/src/main/java/blackjack/model/CardStatus.java b/src/main/java/blackjack/model/Hand.java similarity index 100% rename from src/main/java/blackjack/model/CardStatus.java rename to src/main/java/blackjack/model/Hand.java diff --git a/src/test/java/blackjack/controller/BlackjackControllerTest.java b/src/test/java/blackjack/controller/BlackjackControllerTest.java index de12bb63320..1cfb979521b 100644 --- a/src/test/java/blackjack/controller/BlackjackControllerTest.java +++ b/src/test/java/blackjack/controller/BlackjackControllerTest.java @@ -30,7 +30,7 @@ void test_checkAddCard_return_false() { } @Test - @DisplayName("카드의 합이 21이상인 경우 카드 추가 지급 불가 ( false 반환 )") + @DisplayName("카드의 합이 21 이하인 경우 카드 추가 지급 가능 ( true 반환 )") void test_checkAddCard_return_true() { Player player = new Player("pobi"); From 00f55da965e742a401298209cfcf83cef380bc28 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Sun, 8 Mar 2026 14:55:43 +0900 Subject: [PATCH 21/81] =?UTF-8?q?refactor:=20Card=20=EA=B0=9D=EC=B2=B4=20?= =?UTF-8?q?=EC=84=A4=EA=B3=84=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/Card.java | 78 ++++-------------------- src/main/java/blackjack/model/Cardx.java | 76 +++++++++++++++++++++++ src/main/java/blackjack/model/Rank.java | 34 +++++++++++ src/main/java/blackjack/model/Suit.java | 16 +++++ 4 files changed, 137 insertions(+), 67 deletions(-) create mode 100644 src/main/java/blackjack/model/Cardx.java create mode 100644 src/main/java/blackjack/model/Rank.java create mode 100644 src/main/java/blackjack/model/Suit.java diff --git a/src/main/java/blackjack/model/Card.java b/src/main/java/blackjack/model/Card.java index ba1a10d41be..8235c320f53 100644 --- a/src/main/java/blackjack/model/Card.java +++ b/src/main/java/blackjack/model/Card.java @@ -1,76 +1,20 @@ package blackjack.model; -public enum Card { - A_SPADE(1, "A스페이드"), - TWO_SPADE(2, "2스페이드"), - THREE_SPADE(3, "3스페이드"), - FOUR_SPADE(4, "4스페이드"), - FIVE_SPADE(5, "5스페이드"), - SIX_SPADE(6, "6스페이드"), - SEVEN_SPADE(7, "7스페이드"), - EIGHT_SPADE(8, "8스페이드"), - NINE_SPADE(9, "9스페이드"), - TEN_SPADE(10, "10스페이드"), - J_SPADE(10, "J스페이드"), - Q_SPADE(10, "Q스페이드"), - K_SPADE(10, "K스페이드"), +public class Card { - A_HEART(1, "A하트"), - TWO_HEART(2, "2하트"), - THREE_HEART(3, "3하트"), - FOUR_HEART(4, "4하트"), - FIVE_HEART(5, "5하트"), - SIX_HEART(6, "6하트"), - SEVEN_HEART(7, "7하트"), - EIGHT_HEART(8, "8하트"), - NINE_HEART(9, "9하트"), - TEN_HEART(10, "10하트"), - J_HEART(10, "J하트"), - Q_HEART(10, "Q하트"), - K_HEART(10, "K하트"), + private final Rank rank; + private final Suit suit; - A_CLOVER(1, "A클로버"), - TWO_CLOVER(2, "2클로버"), - THREE_CLOVER(3, "3클로버"), - FOUR_CLOVER(4, "4클로버"), - FIVE_CLOVER(5, "5클로버"), - SIX_CLOVER(6, "6클로버"), - SEVEN_CLOVER(7, "7클로버"), - EIGHT_CLOVER(8, "8클로버"), - NINE_CLOVER(9, "9클로버"), - TEN_CLOVER(10, "10클로버"), - J_CLOVER(10, "J클로버"), - Q_CLOVER(10, "Q클로버"), - K_CLOVER(10, "K클로버"), - - A_DIA(1, "A다이아몬드"), - TWO_DIA(2, "2다이아몬드"), - THREE_DIA(3, "3다이아몬드"), - FOUR_DIA(4, "4다이아몬드"), - FIVE_DIA(5, "5다이아몬드"), - SIX_DIA(6, "6다이아몬드"), - SEVEN_DIA(7, "7다이아몬드"), - EIGHT_DIA(8, "8다이아몬드"), - NINE_DIA(9, "9다이아몬드"), - TEN_DIA(10, "10다이아몬드"), - J_DIA(10, "J다이아몬드"), - Q_DIA(10, "Q다이아몬드"), - K_DIA(10, "K다이아몬드"), - ; - - private int number; - private String format; - - Card(int number, String format) { - this.number = number; - this.format = format; + public Card(Rank rank, Suit suit) { + this.rank = rank; + this.suit = suit; } - public int getNumber() { - return number; + public Rank getRank() { + return rank; } - public String getFormat() { - return format; + public int score() { + return rank.getScore(); } -} \ No newline at end of file +} diff --git a/src/main/java/blackjack/model/Cardx.java b/src/main/java/blackjack/model/Cardx.java new file mode 100644 index 00000000000..ba1a10d41be --- /dev/null +++ b/src/main/java/blackjack/model/Cardx.java @@ -0,0 +1,76 @@ +package blackjack.model; + +public enum Card { + A_SPADE(1, "A스페이드"), + TWO_SPADE(2, "2스페이드"), + THREE_SPADE(3, "3스페이드"), + FOUR_SPADE(4, "4스페이드"), + FIVE_SPADE(5, "5스페이드"), + SIX_SPADE(6, "6스페이드"), + SEVEN_SPADE(7, "7스페이드"), + EIGHT_SPADE(8, "8스페이드"), + NINE_SPADE(9, "9스페이드"), + TEN_SPADE(10, "10스페이드"), + J_SPADE(10, "J스페이드"), + Q_SPADE(10, "Q스페이드"), + K_SPADE(10, "K스페이드"), + + A_HEART(1, "A하트"), + TWO_HEART(2, "2하트"), + THREE_HEART(3, "3하트"), + FOUR_HEART(4, "4하트"), + FIVE_HEART(5, "5하트"), + SIX_HEART(6, "6하트"), + SEVEN_HEART(7, "7하트"), + EIGHT_HEART(8, "8하트"), + NINE_HEART(9, "9하트"), + TEN_HEART(10, "10하트"), + J_HEART(10, "J하트"), + Q_HEART(10, "Q하트"), + K_HEART(10, "K하트"), + + A_CLOVER(1, "A클로버"), + TWO_CLOVER(2, "2클로버"), + THREE_CLOVER(3, "3클로버"), + FOUR_CLOVER(4, "4클로버"), + FIVE_CLOVER(5, "5클로버"), + SIX_CLOVER(6, "6클로버"), + SEVEN_CLOVER(7, "7클로버"), + EIGHT_CLOVER(8, "8클로버"), + NINE_CLOVER(9, "9클로버"), + TEN_CLOVER(10, "10클로버"), + J_CLOVER(10, "J클로버"), + Q_CLOVER(10, "Q클로버"), + K_CLOVER(10, "K클로버"), + + A_DIA(1, "A다이아몬드"), + TWO_DIA(2, "2다이아몬드"), + THREE_DIA(3, "3다이아몬드"), + FOUR_DIA(4, "4다이아몬드"), + FIVE_DIA(5, "5다이아몬드"), + SIX_DIA(6, "6다이아몬드"), + SEVEN_DIA(7, "7다이아몬드"), + EIGHT_DIA(8, "8다이아몬드"), + NINE_DIA(9, "9다이아몬드"), + TEN_DIA(10, "10다이아몬드"), + J_DIA(10, "J다이아몬드"), + Q_DIA(10, "Q다이아몬드"), + K_DIA(10, "K다이아몬드"), + ; + + private int number; + private String format; + + Card(int number, String format) { + this.number = number; + this.format = format; + } + + public int getNumber() { + return number; + } + + public String getFormat() { + return format; + } +} \ No newline at end of file diff --git a/src/main/java/blackjack/model/Rank.java b/src/main/java/blackjack/model/Rank.java new file mode 100644 index 00000000000..12447254fd1 --- /dev/null +++ b/src/main/java/blackjack/model/Rank.java @@ -0,0 +1,34 @@ +package blackjack.model; + +public enum Rank { + + ACE("A", 1), + TWO("2", 2), + THREE("3", 3), + FOUR("4", 4), + FIVE("5", 5), + SIX("6", 6), + SEVEN("7", 7), + EIGHT("8", 8), + NINE("9", 9), + J("J", 10), + Q("Q", 10), + K("K", 10), + ; + + private final String format; + private final int score; + + Rank(String format, int score) { + this.format = format; + this.score = score; + } + + public String getFormat() { + return format; + } + + public int getScore() { + return score; + } +} diff --git a/src/main/java/blackjack/model/Suit.java b/src/main/java/blackjack/model/Suit.java new file mode 100644 index 00000000000..8360a4d4ba4 --- /dev/null +++ b/src/main/java/blackjack/model/Suit.java @@ -0,0 +1,16 @@ +package blackjack.model; + +public enum Suit { + + SPADE("스페이드"), + DIAMOND("다이아몬드"), + HEART("하트"), + CLOVER("클로버"), + ; + + private final String format; + + Suit(String format) { + this.format = format; + } +} From 0075c486ee7482a966bf428276822542f3861081 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Sun, 8 Mar 2026 15:08:11 +0900 Subject: [PATCH 22/81] =?UTF-8?q?refactor:=20=EC=9D=B4=EB=A6=84=20?= =?UTF-8?q?=EA=B0=92=EA=B0=9D=EC=B2=B4=20=EC=83=9D=EC=84=B1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/User.java | 14 ++++----- src/main/java/blackjack/model/UserName.java | 35 +++++++++++++++++++++ 2 files changed, 42 insertions(+), 7 deletions(-) create mode 100644 src/main/java/blackjack/model/UserName.java diff --git a/src/main/java/blackjack/model/User.java b/src/main/java/blackjack/model/User.java index 8e4bc795ed3..1bbe7bfd853 100644 --- a/src/main/java/blackjack/model/User.java +++ b/src/main/java/blackjack/model/User.java @@ -4,23 +4,23 @@ public class User { - private final String name; - private final CardStatus cardStatus; + private final UserName name; + private final Hand hand; public User(String name) { - this.name = name; - this.cardStatus = new CardStatus(); + this.name = new UserName(name); + this.hand = new Hand(); } public String getName() { - return name; + return name.getName(); } public List cards() { - return cardStatus.getCards(); + return hand.getCards(); } public void addCard(Card card) { - cardStatus.addCard(card); + hand.addCard(card); } } diff --git a/src/main/java/blackjack/model/UserName.java b/src/main/java/blackjack/model/UserName.java new file mode 100644 index 00000000000..1b5b829617e --- /dev/null +++ b/src/main/java/blackjack/model/UserName.java @@ -0,0 +1,35 @@ +package blackjack.model; + +import static blackjack.model.ErrorMessage.ERROR_EMPTY_INPUT; +import static blackjack.model.ErrorMessage.ERROR_INVALID_PLAYER_NAME; + +import java.util.regex.Pattern; + +public class UserName { + + private static final String PLAYER_NAME_REGREX = "^[a-zA-Z가-힣]*$"; + + private final String name; + + public UserName(String name) { + validateEmpty(name); + validateRegrex(name); + this.name = name; + } + + public String getName() { + return name; + } + + private void validateEmpty(String name) { + if (name.isEmpty()) { + throw new IllegalArgumentException(ERROR_EMPTY_INPUT.getErrorMessage()); + } + } + + public static void validateRegrex(String name) { + if (!Pattern.matches(PLAYER_NAME_REGREX, name)) { + throw new IllegalArgumentException(ERROR_INVALID_PLAYER_NAME.getErrorMessage()); + } + } +} From 0fa789ccfda5feef262f58588a0b8cb37c5b14e2 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Sun, 8 Mar 2026 15:09:45 +0900 Subject: [PATCH 23/81] =?UTF-8?q?refactor:=20name=20=EA=B0=92=EA=B0=9D?= =?UTF-8?q?=EC=B2=B4=20=EC=83=9D=EC=84=B1=EC=97=90=20=EB=94=B0=EB=A5=B8=20?= =?UTF-8?q?=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/util/PlayerParser.java | 5 ----- 1 file changed, 5 deletions(-) diff --git a/src/main/java/blackjack/util/PlayerParser.java b/src/main/java/blackjack/util/PlayerParser.java index 55f41fe392c..0037a13fbac 100644 --- a/src/main/java/blackjack/util/PlayerParser.java +++ b/src/main/java/blackjack/util/PlayerParser.java @@ -9,14 +9,9 @@ public class PlayerParser { - private static final String PLAYER_NAME_REGREX = "^[a-zA-Z가-힣]*$"; - public static List parse(String names) { return Arrays.stream(names.split(",")) .map(String::trim) - .peek((name) -> Validator.validateRegrex(PLAYER_NAME_REGREX, name, - ERROR_INVALID_PLAYER_NAME.getErrorMessage())) - .peek((name) -> Validator.validateEmpty(name, ERROR_EMPTY_INPUT.getErrorMessage())) .map(Player::new) .toList(); } From 05dc9f37bc5f2c9d39dd638883cf5935b1cf6b0c Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Sun, 8 Mar 2026 15:16:11 +0900 Subject: [PATCH 24/81] =?UTF-8?q?refactor:=20=EC=B9=B4=EB=93=9C=20?= =?UTF-8?q?=EC=B6=94=EA=B0=80=20=EC=97=AC=EB=B6=80=20=EC=9E=85=EB=A0=A5?= =?UTF-8?q?=EA=B0=92=20=EA=B0=9D=EC=B2=B4=20=EC=83=9D=EC=84=B1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/CardAddCmd.java | 35 +++++++++++++++++++ src/main/java/blackjack/util/Validator.java | 20 ----------- 2 files changed, 35 insertions(+), 20 deletions(-) create mode 100644 src/main/java/blackjack/model/CardAddCmd.java delete mode 100644 src/main/java/blackjack/util/Validator.java diff --git a/src/main/java/blackjack/model/CardAddCmd.java b/src/main/java/blackjack/model/CardAddCmd.java new file mode 100644 index 00000000000..af9de2be910 --- /dev/null +++ b/src/main/java/blackjack/model/CardAddCmd.java @@ -0,0 +1,35 @@ +package blackjack.model; + +import static blackjack.model.ErrorMessage.ERROR_EMPTY_INPUT; +import static blackjack.model.ErrorMessage.ERROR_NOT_Y_N_INPUT; + +import java.util.regex.Pattern; + +public class CardAddCmd { + + private static final String Y_N_REGREX = "^[yYnN]$"; + + private final String command; + + public CardAddCmd(String command) { + validateEmpty(command); + validateRegrex(command); + this.command = command; + } + + public boolean isY() { + return command.equals("y") || command.equals("Y"); + } + + private void validateEmpty(String command) { + if (command.isEmpty()) { + throw new IllegalArgumentException(ERROR_EMPTY_INPUT.getErrorMessage()); + } + } + + private void validateRegrex(String command) { + if (!Pattern.matches(Y_N_REGREX, command)) { + throw new IllegalArgumentException(ERROR_NOT_Y_N_INPUT.getErrorMessage()); + } + } +} diff --git a/src/main/java/blackjack/util/Validator.java b/src/main/java/blackjack/util/Validator.java deleted file mode 100644 index 0a657231a3d..00000000000 --- a/src/main/java/blackjack/util/Validator.java +++ /dev/null @@ -1,20 +0,0 @@ -package blackjack.util; - -import static blackjack.model.ErrorMessage.ERROR_EMPTY_INPUT; - -import java.util.regex.Pattern; - -public class Validator { - - public static void validateRegrex(String regrex, String input, String errorMessage) { - if (!Pattern.matches(regrex, input)) { - throw new IllegalArgumentException(errorMessage); - } - } - - public static void validateEmpty(String input, String errorMessage) { - if (input.isEmpty()) { - throw new IllegalArgumentException(ERROR_EMPTY_INPUT.getErrorMessage()); - } - } -} From 7abdbed22a50cbc946e631926a1435eef0e69f2c Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 15:40:36 +0900 Subject: [PATCH 25/81] =?UTF-8?q?refactor:=20User=20=EC=B6=94=EC=83=81=20?= =?UTF-8?q?=ED=81=B4=EB=9E=98=EC=8A=A4=EB=A1=9C=20=EB=B3=80=EA=B2=BD=20&?= =?UTF-8?q?=20=EC=B6=94=EC=83=81=20=EB=A9=94=EC=84=9C=EB=93=9C=20=EC=B6=94?= =?UTF-8?q?=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/Cardx.java | 76 ------------------- src/main/java/blackjack/model/Dealer.java | 5 ++ .../{CardAddCmd.java => HitCommand.java} | 0 src/main/java/blackjack/model/Player.java | 5 ++ src/main/java/blackjack/model/User.java | 16 +++- 5 files changed, 25 insertions(+), 77 deletions(-) delete mode 100644 src/main/java/blackjack/model/Cardx.java rename src/main/java/blackjack/model/{CardAddCmd.java => HitCommand.java} (100%) diff --git a/src/main/java/blackjack/model/Cardx.java b/src/main/java/blackjack/model/Cardx.java deleted file mode 100644 index ba1a10d41be..00000000000 --- a/src/main/java/blackjack/model/Cardx.java +++ /dev/null @@ -1,76 +0,0 @@ -package blackjack.model; - -public enum Card { - A_SPADE(1, "A스페이드"), - TWO_SPADE(2, "2스페이드"), - THREE_SPADE(3, "3스페이드"), - FOUR_SPADE(4, "4스페이드"), - FIVE_SPADE(5, "5스페이드"), - SIX_SPADE(6, "6스페이드"), - SEVEN_SPADE(7, "7스페이드"), - EIGHT_SPADE(8, "8스페이드"), - NINE_SPADE(9, "9스페이드"), - TEN_SPADE(10, "10스페이드"), - J_SPADE(10, "J스페이드"), - Q_SPADE(10, "Q스페이드"), - K_SPADE(10, "K스페이드"), - - A_HEART(1, "A하트"), - TWO_HEART(2, "2하트"), - THREE_HEART(3, "3하트"), - FOUR_HEART(4, "4하트"), - FIVE_HEART(5, "5하트"), - SIX_HEART(6, "6하트"), - SEVEN_HEART(7, "7하트"), - EIGHT_HEART(8, "8하트"), - NINE_HEART(9, "9하트"), - TEN_HEART(10, "10하트"), - J_HEART(10, "J하트"), - Q_HEART(10, "Q하트"), - K_HEART(10, "K하트"), - - A_CLOVER(1, "A클로버"), - TWO_CLOVER(2, "2클로버"), - THREE_CLOVER(3, "3클로버"), - FOUR_CLOVER(4, "4클로버"), - FIVE_CLOVER(5, "5클로버"), - SIX_CLOVER(6, "6클로버"), - SEVEN_CLOVER(7, "7클로버"), - EIGHT_CLOVER(8, "8클로버"), - NINE_CLOVER(9, "9클로버"), - TEN_CLOVER(10, "10클로버"), - J_CLOVER(10, "J클로버"), - Q_CLOVER(10, "Q클로버"), - K_CLOVER(10, "K클로버"), - - A_DIA(1, "A다이아몬드"), - TWO_DIA(2, "2다이아몬드"), - THREE_DIA(3, "3다이아몬드"), - FOUR_DIA(4, "4다이아몬드"), - FIVE_DIA(5, "5다이아몬드"), - SIX_DIA(6, "6다이아몬드"), - SEVEN_DIA(7, "7다이아몬드"), - EIGHT_DIA(8, "8다이아몬드"), - NINE_DIA(9, "9다이아몬드"), - TEN_DIA(10, "10다이아몬드"), - J_DIA(10, "J다이아몬드"), - Q_DIA(10, "Q다이아몬드"), - K_DIA(10, "K다이아몬드"), - ; - - private int number; - private String format; - - Card(int number, String format) { - this.number = number; - this.format = format; - } - - public int getNumber() { - return number; - } - - public String getFormat() { - return format; - } -} \ No newline at end of file diff --git a/src/main/java/blackjack/model/Dealer.java b/src/main/java/blackjack/model/Dealer.java index 5bc061c9142..7c7dd62e40b 100644 --- a/src/main/java/blackjack/model/Dealer.java +++ b/src/main/java/blackjack/model/Dealer.java @@ -17,4 +17,9 @@ public EnumMap getGameResults() { public void addResult(GameResult gameResult) { gameResults.put(gameResult, gameResults.getOrDefault(gameResult, 0) + 1); } + + @Override + public boolean isHitAvailable() { + return totalScore() < Constant.DEALER_ADD_CARD_STAND; + } } diff --git a/src/main/java/blackjack/model/CardAddCmd.java b/src/main/java/blackjack/model/HitCommand.java similarity index 100% rename from src/main/java/blackjack/model/CardAddCmd.java rename to src/main/java/blackjack/model/HitCommand.java diff --git a/src/main/java/blackjack/model/Player.java b/src/main/java/blackjack/model/Player.java index 7bb937cc868..adc57cc750f 100644 --- a/src/main/java/blackjack/model/Player.java +++ b/src/main/java/blackjack/model/Player.java @@ -16,4 +16,9 @@ public GameResult getGameResult() { public void mark(GameResult gameResult) { this.gameResult = gameResult; } + + @Override + public boolean isHitAvailable() { + return totalScore() < Constant.BLACKJACK_SCORE; + } } diff --git a/src/main/java/blackjack/model/User.java b/src/main/java/blackjack/model/User.java index 1bbe7bfd853..713da04cf38 100644 --- a/src/main/java/blackjack/model/User.java +++ b/src/main/java/blackjack/model/User.java @@ -2,7 +2,7 @@ import java.util.List; -public class User { +public abstract class User { private final UserName name; private final Hand hand; @@ -23,4 +23,18 @@ public List cards() { public void addCard(Card card) { hand.addCard(card); } + + public boolean isBlackjack() { + return hand.isBlackjack(); + } + + public boolean isBust() { + return hand.isBust(); + } + + public int totalScore() { + return hand.calculateTotalScore(); + } + + public abstract boolean isHitAvailable(); } From b9ac11c7b4c3d6575817dc57d4ee7a1bb20f4c91 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 15:41:06 +0900 Subject: [PATCH 26/81] =?UTF-8?q?refactor:=20Users=20=EA=B0=9D=EC=B2=B4=20?= =?UTF-8?q?=EC=83=9D=EC=84=B1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/Users.java | 30 ++++++++++++++++++++++++ 1 file changed, 30 insertions(+) create mode 100644 src/main/java/blackjack/model/Users.java diff --git a/src/main/java/blackjack/model/Users.java b/src/main/java/blackjack/model/Users.java new file mode 100644 index 00000000000..f4aabe005e3 --- /dev/null +++ b/src/main/java/blackjack/model/Users.java @@ -0,0 +1,30 @@ +package blackjack.model; + +import blackjack.util.PlayerParser; +import java.util.ArrayList; +import java.util.List; + +public class Users { + + private final List players; + private final Dealer dealer; + + public Users(String playerNames) { + this.players = PlayerParser.parse(playerNames); + this.dealer = new Dealer(); + } + + public List getPlayers() { + return List.copyOf(players); + } + + public Dealer getDealer() { + return dealer; + } + + public List getUsers() { + List users = new ArrayList<>(List.copyOf(players)); + users.add(dealer); + return users; + } +} From 64a8d085e7657d7ea58956e79967476507ac8171 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 15:42:39 +0900 Subject: [PATCH 27/81] =?UTF-8?q?refactor:=20=ED=81=B4=EB=9E=98=EC=8A=A4?= =?UTF-8?q?=EB=AA=85=20=EB=B3=80=EA=B2=BD=20&=20CardCalculator=20=EC=B1=85?= =?UTF-8?q?=EC=9E=84=20=EC=9C=84=EC=9E=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/Hand.java | 56 +++++++++++++++++++++++-- 1 file changed, 53 insertions(+), 3 deletions(-) diff --git a/src/main/java/blackjack/model/Hand.java b/src/main/java/blackjack/model/Hand.java index 64600107792..66b40edf788 100644 --- a/src/main/java/blackjack/model/Hand.java +++ b/src/main/java/blackjack/model/Hand.java @@ -1,21 +1,71 @@ package blackjack.model; +import static blackjack.model.Constant.ACE_SCORE_ELEVEN; +import static blackjack.model.Constant.ACE_SCORE_ONE; +import static blackjack.model.Constant.INIT_CARDS_END_IDX; +import static blackjack.model.Constant.INIT_CARDS_START_IDX; +import static blackjack.model.Constant.BLACKJACK_SCORE; + import java.util.ArrayList; import java.util.List; +import java.util.Map; +import java.util.stream.Collectors; -public class CardStatus { +public class Hand { private final List cards; - public CardStatus() { + public Hand() { this.cards = new ArrayList<>(); } public List getCards() { - return cards; + return List.copyOf(cards); } public void addCard(Card card) { cards.add(card); } + + public boolean isBlackjack() { + List initCards = cards.subList(INIT_CARDS_START_IDX, INIT_CARDS_END_IDX); + return totalScore(initCards) == BLACKJACK_SCORE; + } + + public boolean isBust() { + return totalScore(cards) > BLACKJACK_SCORE; + } + + public boolean isHitAvailable() { + return totalScore(cards) >= BLACKJACK_SCORE; + } + + public int calculateTotalScore() { + return totalScore(cards); + } + + public int totalScore(List cards) { + Map> partitioned = cards.stream() + .collect(Collectors.partitioningBy(card -> card.getRank() == Rank.ACE)); + + List aceCards = partitioned.get(true); // Ace인 카드들 + List nonAceCards = partitioned.get(false);// Ace가 아닌 카드들 + int totalScoreNonAce = nonAceCards.stream() + .mapToInt(Card::score) + .sum(); + + return addAceScore(aceCards, totalScoreNonAce); + } + + int addAceScore(List aceCards, int totalScore) { + for (int i = 0; i < aceCards.size(); i++) { + if (totalScore + ACE_SCORE_ELEVEN > BLACKJACK_SCORE) { + totalScore += ACE_SCORE_ONE; + continue; + } + totalScore += ACE_SCORE_ELEVEN; + } + + return totalScore; + } } From 9719248311790bb7121a0c0289c36c2674661811 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 15:43:11 +0900 Subject: [PATCH 28/81] =?UTF-8?q?chore:=20=EC=83=81=EC=88=98=EB=AA=85=20?= =?UTF-8?q?=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/Constant.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/blackjack/model/Constant.java b/src/main/java/blackjack/model/Constant.java index 233e45e55d4..66b9a546f6c 100644 --- a/src/main/java/blackjack/model/Constant.java +++ b/src/main/java/blackjack/model/Constant.java @@ -3,7 +3,7 @@ public class Constant { public static final int DEALER_ADD_CARD_STAND = 17; - public static final int TWENTY_ONE = 21; + public static final int BLACKJACK_SCORE = 21; public static final int INIT_CARDS_START_IDX = 0; public static final int INIT_CARDS_END_IDX = 2; From 417f72f1892242ca81ac9c9c68255b49b72eb233 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 15:43:58 +0900 Subject: [PATCH 29/81] =?UTF-8?q?refactor:=20=ED=81=B4=EB=9E=98=EC=8A=A4?= =?UTF-8?q?=EB=AA=85=20=EC=88=98=EC=A0=95=20&=20=EB=A9=94=EC=84=9C?= =?UTF-8?q?=EB=93=9C=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/HitCommand.java | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/main/java/blackjack/model/HitCommand.java b/src/main/java/blackjack/model/HitCommand.java index af9de2be910..d0e2ce47173 100644 --- a/src/main/java/blackjack/model/HitCommand.java +++ b/src/main/java/blackjack/model/HitCommand.java @@ -5,22 +5,18 @@ import java.util.regex.Pattern; -public class CardAddCmd { +public class HitCommand { private static final String Y_N_REGREX = "^[yYnN]$"; private final String command; - public CardAddCmd(String command) { + public HitCommand(String command) { validateEmpty(command); validateRegrex(command); this.command = command; } - public boolean isY() { - return command.equals("y") || command.equals("Y"); - } - private void validateEmpty(String command) { if (command.isEmpty()) { throw new IllegalArgumentException(ERROR_EMPTY_INPUT.getErrorMessage()); @@ -32,4 +28,8 @@ private void validateRegrex(String command) { throw new IllegalArgumentException(ERROR_NOT_Y_N_INPUT.getErrorMessage()); } } + + public boolean isY() { + return command.equals("y") || command.equals("Y"); + } } From 19a74ec25b369d0759343e0a15341513a2f698e5 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 15:44:19 +0900 Subject: [PATCH 30/81] =?UTF-8?q?chore:=20getter=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/Suit.java | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/main/java/blackjack/model/Suit.java b/src/main/java/blackjack/model/Suit.java index 8360a4d4ba4..fd20dc7858c 100644 --- a/src/main/java/blackjack/model/Suit.java +++ b/src/main/java/blackjack/model/Suit.java @@ -13,4 +13,8 @@ public enum Suit { Suit(String format) { this.format = format; } + + public String getFormat() { + return format; + } } From a4cdc0efd959fb449094662d41742b9797c700a9 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 15:44:38 +0900 Subject: [PATCH 31/81] =?UTF-8?q?chore:=20getter=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/Card.java | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/main/java/blackjack/model/Card.java b/src/main/java/blackjack/model/Card.java index 8235c320f53..c127ed760bf 100644 --- a/src/main/java/blackjack/model/Card.java +++ b/src/main/java/blackjack/model/Card.java @@ -14,6 +14,10 @@ public Rank getRank() { return rank; } + public Suit getSuit() { + return suit; + } + public int score() { return rank.getScore(); } From 32383b40d97cd1839200017058403525d6e9b0ba Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 15:46:18 +0900 Subject: [PATCH 32/81] =?UTF-8?q?refactor:=20=EB=8D=B1=20=EC=B4=88?= =?UTF-8?q?=EA=B8=B0=ED=99=94=20=EB=A1=9C=EC=A7=81=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/CardProvider.java | 17 ++++++++++++----- 1 file changed, 12 insertions(+), 5 deletions(-) diff --git a/src/main/java/blackjack/model/CardProvider.java b/src/main/java/blackjack/model/CardProvider.java index 141da1f2ded..f6982c2c356 100644 --- a/src/main/java/blackjack/model/CardProvider.java +++ b/src/main/java/blackjack/model/CardProvider.java @@ -18,23 +18,30 @@ public CardProvider() { private void initDeck() { List cards = new ArrayList<>(); - for (Card card : Card.values()) { - cards.add(card); + for (Rank rank : Rank.values()) { + for (Suit suit : Suit.values()) { + cards.add(new Card(rank, suit)); + } } Collections.shuffle(cards); this.deck.addAll(cards); } - public void provideInitCards(List players, Dealer dealer) { + public void provideInitCards(Users users) { + List players = users.getPlayers(); + Dealer dealer = users.getDealer(); for (int i = INIT_CARDS_START_IDX; i < INIT_CARDS_END_IDX; i++) { for (Player player : players) { - player.addCard(deck.poll()); + provideOneCard(player); } - dealer.addCard(deck.poll()); + provideOneCard(dealer); } } public void provideOneCard(User user) { + if (deck.peek() == null) { + + } user.addCard(deck.poll()); } } From b0622b2a2c71a47d3c44b3ea91b315cee1bfc1ac Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 15:59:41 +0900 Subject: [PATCH 33/81] =?UTF-8?q?refactor:=20CardCalculator=20=EC=A0=9C?= =?UTF-8?q?=EA=B1=B0=20->=20Hand=EB=A1=9C=20=EC=97=AD=ED=95=A0=20=EC=9C=84?= =?UTF-8?q?=EC=9E=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../java/blackjack/model/CardCalculator.java | 53 ------------------- 1 file changed, 53 deletions(-) delete mode 100644 src/main/java/blackjack/model/CardCalculator.java diff --git a/src/main/java/blackjack/model/CardCalculator.java b/src/main/java/blackjack/model/CardCalculator.java deleted file mode 100644 index 8a6da8dde50..00000000000 --- a/src/main/java/blackjack/model/CardCalculator.java +++ /dev/null @@ -1,53 +0,0 @@ -package blackjack.model; - -import static blackjack.model.Constant.ACE_SCORE_ELEVEN; -import static blackjack.model.Constant.ACE_SCORE_ONE; -import static blackjack.model.Constant.INIT_CARDS_END_IDX; -import static blackjack.model.Constant.INIT_CARDS_START_IDX; -import static blackjack.model.Constant.TWENTY_ONE; - -import java.util.List; -import java.util.Map; -import java.util.stream.Collectors; - -public class CardCalculator { - - public boolean calculateBlackjack(List cards) { - List initCards = cards.subList(INIT_CARDS_START_IDX, INIT_CARDS_END_IDX); - return totalScore(initCards) == TWENTY_ONE; - } - - public int totalScore(List cards) { - Map> partitioned = cards.stream() - .collect(Collectors.partitioningBy(card -> - card.equals(Card.A_CLOVER) || - card.equals(Card.A_DIA) || - card.equals(Card.A_SPADE) || - card.equals(Card.A_HEART) - )); - - List aceCards = partitioned.get(true); // Ace인 카드들 - List nonAceCards = partitioned.get(false);// Ace가 아닌 카드들 - int totalScoreNonAce = nonAceCards.stream() - .mapToInt(Card::getNumber) - .sum(); - - return addAceScore(aceCards, totalScoreNonAce); - } - - public boolean calculateBust(int totalScore) { - return totalScore > TWENTY_ONE; - } - - int addAceScore(List aceCards, int totalScore) { - for (int i = 0; i < aceCards.size(); i++) { - if (totalScore + ACE_SCORE_ELEVEN > TWENTY_ONE) { - totalScore += ACE_SCORE_ONE; - continue; - } - totalScore += ACE_SCORE_ELEVEN; - } - - return totalScore; - } -} \ No newline at end of file From ded3f8b9c5377fdba0256d8dbc9a9151193190de Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 16:06:09 +0900 Subject: [PATCH 34/81] =?UTF-8?q?refactor:=20=EB=8D=B1=EC=9D=B4=20?= =?UTF-8?q?=EC=86=8C=EC=A7=84=EB=90=9C=20=EA=B2=BD=EC=9A=B0=20=EB=8D=B1=20?= =?UTF-8?q?=EC=9E=AC=EC=83=9D=EC=84=B1=20=EB=A1=9C=EC=A7=81=20=EC=B6=94?= =?UTF-8?q?=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/CardProvider.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/blackjack/model/CardProvider.java b/src/main/java/blackjack/model/CardProvider.java index f6982c2c356..dea6b37ab4c 100644 --- a/src/main/java/blackjack/model/CardProvider.java +++ b/src/main/java/blackjack/model/CardProvider.java @@ -40,7 +40,7 @@ public void provideInitCards(Users users) { public void provideOneCard(User user) { if (deck.peek() == null) { - + initDeck(); } user.addCard(deck.poll()); } From b85d895e1c0b2813fd167df7d05e16317ead377a Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 17:19:49 +0900 Subject: [PATCH 35/81] =?UTF-8?q?refactor:=20GameResultCalculator=20?= =?UTF-8?q?=ED=81=B4=EB=9E=98=EC=8A=A4=20=EC=82=AD=EC=84=B8=20&=20Users=20?= =?UTF-8?q?=ED=81=B4=EB=9E=98=EC=8A=A4=EB=A1=9C=20=EC=97=AD=ED=95=A0=20?= =?UTF-8?q?=EC=9C=84=EC=9E=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/Application.java | 8 +- .../blackjack/model/GameResultCalculator.java | 88 ------------------- src/main/java/blackjack/model/Users.java | 67 ++++++++++++++ 3 files changed, 68 insertions(+), 95 deletions(-) delete mode 100644 src/main/java/blackjack/model/GameResultCalculator.java diff --git a/src/main/java/blackjack/Application.java b/src/main/java/blackjack/Application.java index 2a8f8fde75c..7ef3bf73678 100644 --- a/src/main/java/blackjack/Application.java +++ b/src/main/java/blackjack/Application.java @@ -1,19 +1,13 @@ package blackjack; import blackjack.controller.BlackjackController; -import blackjack.model.CardCalculator; import blackjack.model.CardProvider; -import blackjack.model.GameResultCalculator; public class Application { public static void main(String[] args) { CardProvider cardProvider = new CardProvider(); - CardCalculator cardCalculator = new CardCalculator(); - GameResultCalculator gameResultCalculator = new GameResultCalculator(); - BlackjackController blackjackController = new BlackjackController(cardProvider, cardCalculator, - gameResultCalculator); + BlackjackController blackjackController = new BlackjackController(cardProvider); blackjackController.run(); - } } diff --git a/src/main/java/blackjack/model/GameResultCalculator.java b/src/main/java/blackjack/model/GameResultCalculator.java deleted file mode 100644 index 2790c4cac18..00000000000 --- a/src/main/java/blackjack/model/GameResultCalculator.java +++ /dev/null @@ -1,88 +0,0 @@ -package blackjack.model; - -import java.util.List; - -public class GameResultCalculator { - public void calculate(List gameSummaries) { - GameSummary dealerGameSummary = gameSummaries.getFirst(); - Dealer dealer = (Dealer) dealerGameSummary.user(); - int dealerTotalScore = dealerGameSummary.totalScore(); - List playerGameSummaries = gameSummaries.subList(1, gameSummaries.size()); - - for (GameSummary playerGameSummary : playerGameSummaries) { - Player player = (Player) playerGameSummary.user(); - int playerTotalScore = playerGameSummary.totalScore(); - - if (calculateWhenBlackjack(playerGameSummary, dealerGameSummary, dealer, player)) { - continue; - } - - if (calculateWhenBust(playerGameSummary, dealerGameSummary, dealer, player)) { - continue; - } - - calculateWhenNormal(dealerTotalScore, playerTotalScore, dealer, player); - } - } - - private static boolean calculateWhenBlackjack(GameSummary playerGameSummary, GameSummary dealerGameSummary, - Dealer dealer, - Player player) { - if (dealerGameSummary.blackjack() && playerGameSummary.blackjack()) { - dealer.addResult(GameResult.DRAW); - return true; - } - - if (playerGameSummary.blackjack()) { - player.mark(GameResult.WIN); - dealer.addResult(GameResult.LOSE); - return true; - } - - if (dealerGameSummary.blackjack()) { - player.mark(GameResult.LOSE); - dealer.addResult(GameResult.WIN); - return true; - } - return false; - } - - private static boolean calculateWhenBust(GameSummary playerGameSummary, GameSummary dealerGameSummary, - Dealer dealer, - Player player) { - if (playerGameSummary.bust() && dealerGameSummary.bust()) { - dealer.addResult(GameResult.WIN); - player.mark(GameResult.LOSE); - return true; - } - - if (playerGameSummary.bust()) { - player.mark(GameResult.LOSE); - dealer.addResult(GameResult.WIN); - return true; - } - - if (dealerGameSummary.bust()) { - dealer.addResult(GameResult.LOSE); - player.mark(GameResult.WIN); - return true; - } - return false; - } - - private static void calculateWhenNormal(int dealerTotalScore, int playerTotalScore, Dealer dealer, Player player) { - if (dealerTotalScore > playerTotalScore) { - dealer.addResult(GameResult.WIN); - player.mark(GameResult.LOSE); - return; - } - - if (dealerTotalScore < playerTotalScore) { - dealer.addResult(GameResult.LOSE); - player.mark(GameResult.WIN); - return; - } - - dealer.addResult(GameResult.DRAW); - } -} \ No newline at end of file diff --git a/src/main/java/blackjack/model/Users.java b/src/main/java/blackjack/model/Users.java index f4aabe005e3..76a7796c334 100644 --- a/src/main/java/blackjack/model/Users.java +++ b/src/main/java/blackjack/model/Users.java @@ -27,4 +27,71 @@ public List getUsers() { users.add(dealer); return users; } + + public void determineWinner() { + for (Player player : players) { + if (calculateWhenBlackjack(player, dealer)) { + continue; + } + + if (calculateWhenBust(player, dealer)) { + continue; + } + + calculateWhenNormal(player, dealer); + } + } + + private boolean calculateWhenBlackjack(Player player, Dealer dealer) { + if (player.isBlackjack() && dealer.isBlackjack()) { + dealer.addResult(GameResult.DRAW); + return true; + } + + if (player.isBlackjack()) { + player.mark(GameResult.WIN); + dealer.addResult(GameResult.LOSE); + return true; + } + + if (dealer.isBlackjack()) { + player.mark(GameResult.LOSE); + dealer.addResult(GameResult.WIN); + return true; + } + + return false; + } + + private boolean calculateWhenBust(Player player, Dealer dealer) { + if (player.isBust()) { + dealer.addResult(GameResult.WIN); + player.mark(GameResult.LOSE); + return true; + } + + if (dealer.isBust()) { + dealer.addResult(GameResult.LOSE); + player.mark(GameResult.WIN); + return true; + } + + return false; + } + + private static void calculateWhenNormal(Player player, Dealer dealer) { + if (player.totalScore() > dealer.totalScore()) { + dealer.addResult(GameResult.LOSE); + player.mark(GameResult.WIN); + return; + } + + if (player.totalScore() < dealer.totalScore()) { + dealer.addResult(GameResult.WIN); + player.mark(GameResult.LOSE); + return; + } + + dealer.addResult(GameResult.DRAW); + } } From fcba50581ac4f110b99f1c2b03afe04af94f1433 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 17:37:15 +0900 Subject: [PATCH 36/81] =?UTF-8?q?refactor:=20=EC=B6=9C=EB=A0=A5=20?= =?UTF-8?q?=EB=A1=9C=EC=A7=81=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/view/OutputView.java | 51 ++++++++++---------- 1 file changed, 26 insertions(+), 25 deletions(-) diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index 08b75bdd219..5e576e568bf 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -1,18 +1,22 @@ package blackjack.view; -import static blackjack.model.Constant.TWENTY_ONE; +import static blackjack.model.Constant.BLACKJACK_SCORE; import blackjack.model.Card; import blackjack.model.Dealer; import blackjack.model.GameResult; -import blackjack.model.GameSummary; import blackjack.model.Player; import blackjack.model.User; +import blackjack.model.Users; import java.util.EnumMap; import java.util.List; +import java.util.stream.Collectors; public class OutputView { - public static void printInitCards(List players, Dealer dealer) { + public static void printInitCards(Users users) { + List players = users.getPlayers(); + Dealer dealer = users.getDealer(); + List names = players.stream() .map(Player::getName) .toList(); @@ -31,52 +35,50 @@ public static void printInitCards(List players, Dealer dealer) { } private static void printDealerCard(Dealer dealer) { - System.out.println("딜러카드: " + dealer.cards().getFirst().getFormat()); + Card firstCard = dealer.cards().getFirst(); + System.out.println("딜러카드: " + firstCard.getRank().getFormat() + firstCard.getSuit().getFormat()); } public static void printPlayerCards(Player player) { - List formats = player.cards().stream() - .map(Card::getFormat) - .toList(); + String cardsFormat = player.cards().stream() + .map(card -> card.getRank().getFormat() + card.getSuit().getFormat()) + .collect(Collectors.joining(", ")); - System.out.println(player.getName() + "카드: " + String.join(", ", formats)); + System.out.println(player.getName() + "카드: " + cardsFormat); } - public static void printCantAddCard() { - System.out.println("카드의 합계가 " + TWENTY_ONE + " 이상입니다. 더이상 카드를 받을 수 없습니다."); + public static void printCantHit() { + System.out.println("카드의 합계가 " + BLACKJACK_SCORE + " 이상입니다. 더이상 카드를 받을 수 없습니다."); } public static void printDealerHit() { System.out.println("\n딜러는 16이하라 한장의 카드를 더 받았습니다.\n"); } - public static void printCardStatus(GameSummary gameSummary) { - User user = gameSummary.user(); - + public static void printHandStatus(Users users) { StringBuilder sb = new StringBuilder(); - sb.append(user.getName() + "카드: "); - List cardFormats = user.cards().stream().map(Card::getFormat).toList(); - sb.append(String.join(", ", cardFormats)); - sb.append(" - 결과: " + gameSummary.totalScore()); - + for (User user : users.getUsers()) { + sb.append(user.getName()).append(" 카드: "); + sb.append(user.cards().stream() + .map(card -> card.getRank().getFormat() + card.getSuit().getFormat()) + .collect(Collectors.joining(", "))); + sb.append(" - 결과: ").append(user.totalScore()).append("\n"); + } System.out.println(sb); } - public static void printGameResult(List users) { + public static void printGameResult(Users users) { System.out.println(); System.out.println("## 최종 승패"); - Dealer dealer = (Dealer) users.getFirst(); + Dealer dealer = users.getDealer(); EnumMap dealerGameResult = dealer.getGameResults(); System.out.println( dealer.getName() + ": " + dealerGameResult.getOrDefault(GameResult.WIN, 0) + "승 " + dealerGameResult.getOrDefault(GameResult.DRAW, 0) + "무 " + dealerGameResult.getOrDefault( GameResult.LOSE, 0) + "패"); - List players = users.stream() - .skip(1) - .map(user -> (Player) user) - .toList(); + List players = users.getPlayers(); for (Player player : players) { System.out.print(player.getName() + ": "); System.out.println(player.getGameResult().getFormat()); @@ -86,5 +88,4 @@ public static void printGameResult(List users) { public static void printError(String errorMessage) { System.out.println("[ERROR] " + errorMessage); } - } From 556d1de046b148c7c2f0f7905765c397b00e1c25 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 23:22:36 +0900 Subject: [PATCH 37/81] =?UTF-8?q?refactor:=20=EC=BD=94=EB=93=9C=20?= =?UTF-8?q?=EC=BB=A8=EB=B2=A4=EC=85=98=20=EC=A0=81=EC=9A=A9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/Application.java | 5 ++--- src/main/java/blackjack/model/CardProvider.java | 1 + src/main/java/blackjack/model/HitCommand.java | 16 ++++++++-------- 3 files changed, 11 insertions(+), 11 deletions(-) diff --git a/src/main/java/blackjack/Application.java b/src/main/java/blackjack/Application.java index 7ef3bf73678..d6e1aebdee6 100644 --- a/src/main/java/blackjack/Application.java +++ b/src/main/java/blackjack/Application.java @@ -4,10 +4,9 @@ import blackjack.model.CardProvider; public class Application { - public static void main(String[] args) { - CardProvider cardProvider = new CardProvider(); - BlackjackController blackjackController = new BlackjackController(cardProvider); + public static void main(String[] args) { + BlackjackController blackjackController = new BlackjackController(new CardProvider()); blackjackController.run(); } } diff --git a/src/main/java/blackjack/model/CardProvider.java b/src/main/java/blackjack/model/CardProvider.java index dea6b37ab4c..3d2e5fe1a0a 100644 --- a/src/main/java/blackjack/model/CardProvider.java +++ b/src/main/java/blackjack/model/CardProvider.java @@ -10,6 +10,7 @@ import java.util.Queue; public class CardProvider { + private final Queue deck = new LinkedList<>(); public CardProvider() { diff --git a/src/main/java/blackjack/model/HitCommand.java b/src/main/java/blackjack/model/HitCommand.java index d0e2ce47173..8f31d6a71ab 100644 --- a/src/main/java/blackjack/model/HitCommand.java +++ b/src/main/java/blackjack/model/HitCommand.java @@ -7,29 +7,29 @@ public class HitCommand { - private static final String Y_N_REGREX = "^[yYnN]$"; + private static final String Y_N_REGEX = "^[yYnN]$"; private final String command; public HitCommand(String command) { validateEmpty(command); - validateRegrex(command); + validateRegex(command); this.command = command; } + public boolean isY() { + return command.equals("y") || command.equals("Y"); + } + private void validateEmpty(String command) { if (command.isEmpty()) { throw new IllegalArgumentException(ERROR_EMPTY_INPUT.getErrorMessage()); } } - private void validateRegrex(String command) { - if (!Pattern.matches(Y_N_REGREX, command)) { + private void validateRegex(String command) { + if (!Pattern.matches(Y_N_REGEX, command)) { throw new IllegalArgumentException(ERROR_NOT_Y_N_INPUT.getErrorMessage()); } } - - public boolean isY() { - return command.equals("y") || command.equals("Y"); - } } From da880c791482ca810b351cfb37d66e9e9271f421 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Mon, 9 Mar 2026 23:23:01 +0900 Subject: [PATCH 38/81] =?UTF-8?q?chore:=20=EB=AF=B8=EC=82=AC=EC=9A=A9=20?= =?UTF-8?q?=EB=9D=BC=EC=9D=B4=EB=B8=8C=EB=9F=AC=EB=A6=AC=20import=20?= =?UTF-8?q?=EC=A0=9C=EA=B1=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/util/PlayerParser.java | 4 ---- 1 file changed, 4 deletions(-) diff --git a/src/main/java/blackjack/util/PlayerParser.java b/src/main/java/blackjack/util/PlayerParser.java index 0037a13fbac..f05ef01653d 100644 --- a/src/main/java/blackjack/util/PlayerParser.java +++ b/src/main/java/blackjack/util/PlayerParser.java @@ -1,8 +1,5 @@ package blackjack.util; -import static blackjack.model.ErrorMessage.ERROR_EMPTY_INPUT; -import static blackjack.model.ErrorMessage.ERROR_INVALID_PLAYER_NAME; - import blackjack.model.Player; import java.util.Arrays; import java.util.List; @@ -15,5 +12,4 @@ public static List parse(String names) { .map(Player::new) .toList(); } - } From 6ba5301d6bea2d4ef5ca573ede6c2bd6028f4771 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 14:33:15 +0900 Subject: [PATCH 39/81] =?UTF-8?q?refactor:=20PlayersGameResult=20=EA=B0=9D?= =?UTF-8?q?=EC=B2=B4=20=EC=83=9D=EC=84=B1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../blackjack/model/PlayersGameResult.java | 6 ++ src/main/java/blackjack/model/Users.java | 58 ++++++++++++------- src/main/java/blackjack/view/OutputView.java | 27 ++++++--- 3 files changed, 63 insertions(+), 28 deletions(-) create mode 100644 src/main/java/blackjack/model/PlayersGameResult.java diff --git a/src/main/java/blackjack/model/PlayersGameResult.java b/src/main/java/blackjack/model/PlayersGameResult.java new file mode 100644 index 00000000000..c564cf5e3c2 --- /dev/null +++ b/src/main/java/blackjack/model/PlayersGameResult.java @@ -0,0 +1,6 @@ +package blackjack.model; + +import java.util.Map; + +public record PlayersGameResult(Map result) { +} diff --git a/src/main/java/blackjack/model/Users.java b/src/main/java/blackjack/model/Users.java index 76a7796c334..2dde1360595 100644 --- a/src/main/java/blackjack/model/Users.java +++ b/src/main/java/blackjack/model/Users.java @@ -2,13 +2,20 @@ import blackjack.util.PlayerParser; import java.util.ArrayList; +import java.util.HashMap; import java.util.List; +import java.util.Map; public class Users { private final List players; private final Dealer dealer; + public Users(List players, Dealer dealer) { + this.players = players; + this.dealer = dealer; + } + public Users(String playerNames) { this.players = PlayerParser.parse(playerNames); this.dealer = new Dealer(); @@ -28,70 +35,81 @@ public List getUsers() { return users; } - public void determineWinner() { + public PlayersGameResult determineWinner() { + Map result = new HashMap<>(); for (Player player : players) { - if (calculateWhenBlackjack(player, dealer)) { + if (calculateWhenBlackjack(player, dealer, result)) { continue; } - if (calculateWhenBust(player, dealer)) { + if (calculateWhenBust(player, dealer, result)) { continue; } - calculateWhenNormal(player, dealer); + calculateWhenNormal(player, dealer, result); } + return new PlayersGameResult(result); } - private boolean calculateWhenBlackjack(Player player, Dealer dealer) { + private boolean calculateWhenBlackjack(Player player, Dealer dealer, Map result) { if (player.isBlackjack() && dealer.isBlackjack()) { - dealer.addResult(GameResult.DRAW); + logDraw(player, dealer, result); return true; } if (player.isBlackjack()) { - player.mark(GameResult.WIN); - dealer.addResult(GameResult.LOSE); + logPlayerWin(player, dealer, result); return true; } if (dealer.isBlackjack()) { - player.mark(GameResult.LOSE); - dealer.addResult(GameResult.WIN); + logPlayerLose(player, dealer, result); return true; } return false; } - private boolean calculateWhenBust(Player player, Dealer dealer) { + private boolean calculateWhenBust(Player player, Dealer dealer, Map result) { if (player.isBust()) { - dealer.addResult(GameResult.WIN); - player.mark(GameResult.LOSE); + logPlayerLose(player, dealer, result); return true; } if (dealer.isBust()) { - dealer.addResult(GameResult.LOSE); - player.mark(GameResult.WIN); + logPlayerWin(player, dealer, result); return true; } return false; } - private static void calculateWhenNormal(Player player, Dealer dealer) { + private void calculateWhenNormal(Player player, Dealer dealer, Map result) { if (player.totalScore() > dealer.totalScore()) { - dealer.addResult(GameResult.LOSE); - player.mark(GameResult.WIN); + logPlayerWin(player, dealer, result); return; } if (player.totalScore() < dealer.totalScore()) { - dealer.addResult(GameResult.WIN); - player.mark(GameResult.LOSE); + logPlayerLose(player, dealer, result); return; } + logDraw(player, dealer, result); + } + + private void logPlayerWin(Player player, Dealer dealer, Map result) { + result.put(player, GameResult.WIN); + dealer.addResult(GameResult.LOSE); + } + + private void logPlayerLose(Player player, Dealer dealer, Map result) { + result.put(player, GameResult.LOSE); + dealer.addResult(GameResult.WIN); + } + + private void logDraw(Player player, Dealer dealer, Map result) { + result.put(player, GameResult.DRAW); dealer.addResult(GameResult.DRAW); } } diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index 5e576e568bf..7465568612d 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -6,10 +6,12 @@ import blackjack.model.Dealer; import blackjack.model.GameResult; import blackjack.model.Player; +import blackjack.model.PlayersGameResult; import blackjack.model.User; import blackjack.model.Users; import java.util.EnumMap; import java.util.List; +import java.util.Map; import java.util.stream.Collectors; public class OutputView { @@ -56,18 +58,27 @@ public static void printDealerHit() { } public static void printHandStatus(Users users) { + Dealer dealer = users.getDealer(); + List players = users.getPlayers(); StringBuilder sb = new StringBuilder(); - for (User user : users.getUsers()) { - sb.append(user.getName()).append(" 카드: "); - sb.append(user.cards().stream() + + sb.append(dealer.getName()).append(" 카드: "); + sb.append(dealer.cards().stream() + .map(card -> card.getRank().getFormat() + card.getSuit().getFormat()) + .collect(Collectors.joining(", "))); + sb.append(" - 결과: ").append(dealer.totalScore()).append("\n"); + + for (Player player : players) { + sb.append(player.getName()).append(" 카드: "); + sb.append(player.cards().stream() .map(card -> card.getRank().getFormat() + card.getSuit().getFormat()) .collect(Collectors.joining(", "))); - sb.append(" - 결과: ").append(user.totalScore()).append("\n"); + sb.append(" - 결과: ").append(player.totalScore()).append("\n"); } System.out.println(sb); } - public static void printGameResult(Users users) { + public static void printGameResult(PlayersGameResult playersGameResult, Users users) { System.out.println(); System.out.println("## 최종 승패"); @@ -78,10 +89,10 @@ public static void printGameResult(Users users) { dealerGameResult.getOrDefault(GameResult.DRAW, 0) + "무 " + dealerGameResult.getOrDefault( GameResult.LOSE, 0) + "패"); - List players = users.getPlayers(); - for (Player player : players) { + Map result = playersGameResult.result(); + for (Player player : users.getPlayers()) { System.out.print(player.getName() + ": "); - System.out.println(player.getGameResult().getFormat()); + System.out.println(result.get(player).getFormat()); } } From 08ce10982b602cc20b524377c23526d9a364f1f0 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 14:33:34 +0900 Subject: [PATCH 40/81] =?UTF-8?q?refactor:=20GameResult=20=ED=95=84?= =?UTF-8?q?=EB=93=9C=20=EC=A0=9C=EA=B1=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/Player.java | 11 ----------- 1 file changed, 11 deletions(-) diff --git a/src/main/java/blackjack/model/Player.java b/src/main/java/blackjack/model/Player.java index adc57cc750f..c83019db6d6 100644 --- a/src/main/java/blackjack/model/Player.java +++ b/src/main/java/blackjack/model/Player.java @@ -2,19 +2,8 @@ public class Player extends User { - private GameResult gameResult; - public Player(String name) { super(name); - this.gameResult = GameResult.DRAW; - } - - public GameResult getGameResult() { - return gameResult; - } - - public void mark(GameResult gameResult) { - this.gameResult = gameResult; } @Override From efdaba9e148bc5a6705af7a1849136dfee073b4b Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 14:34:01 +0900 Subject: [PATCH 41/81] =?UTF-8?q?refactor:=20addAceScore()=20=EC=A0=91?= =?UTF-8?q?=EA=B7=BC=20=EC=A0=9C=EC=96=B4=EC=9E=90=20private=EC=9C=BC?= =?UTF-8?q?=EB=A1=9C=20=EB=B3=80=EA=B2=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/Hand.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/blackjack/model/Hand.java b/src/main/java/blackjack/model/Hand.java index 66b40edf788..825909f9fa8 100644 --- a/src/main/java/blackjack/model/Hand.java +++ b/src/main/java/blackjack/model/Hand.java @@ -57,7 +57,7 @@ public int totalScore(List cards) { return addAceScore(aceCards, totalScoreNonAce); } - int addAceScore(List aceCards, int totalScore) { + private int addAceScore(List aceCards, int totalScore) { for (int i = 0; i < aceCards.size(); i++) { if (totalScore + ACE_SCORE_ELEVEN > BLACKJACK_SCORE) { totalScore += ACE_SCORE_ONE; From c375bae7ed434da3ae3392a1268cc87d48069d4a Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 14:36:28 +0900 Subject: [PATCH 42/81] =?UTF-8?q?refactor:=20Controller=20=EC=B1=85?= =?UTF-8?q?=EC=9E=84=20=EB=B6=84=EB=A6=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../controller/BlackjackController.java | 98 +++++++------------ 1 file changed, 37 insertions(+), 61 deletions(-) diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index f3e45c88d89..94eb7a415c3 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -1,86 +1,54 @@ package blackjack.controller; -import static blackjack.model.Constant.DEALER_ADD_CARD_STAND; -import static blackjack.model.Constant.TWENTY_ONE; import static blackjack.util.ExceptionHandler.retryUntilSuccess; -import blackjack.model.CardCalculator; +import blackjack.model.HitCommand; import blackjack.model.CardProvider; import blackjack.model.Dealer; -import blackjack.model.ErrorMessage; -import blackjack.model.GameResultCalculator; -import blackjack.model.GameSummary; import blackjack.model.Player; -import blackjack.model.User; -import blackjack.util.PlayerParser; -import blackjack.util.Validator; +import blackjack.model.PlayersGameResult; +import blackjack.model.Users; import blackjack.view.InputView; import blackjack.view.OutputView; -import java.util.ArrayList; import java.util.List; public class BlackjackController { - private static final String Y_N_REGREX = "^[yYnN]$"; - private final CardProvider cardProvider; - private final CardCalculator cardCalculator; - private final GameResultCalculator gameResultCalculator; - public BlackjackController(CardProvider cardProvider, CardCalculator cardCalculator, - GameResultCalculator gameResultCalculator) { + public BlackjackController(CardProvider cardProvider) { this.cardProvider = cardProvider; - this.cardCalculator = cardCalculator; - this.gameResultCalculator = gameResultCalculator; } public void run() { - List players = retryUntilSuccess(() -> { - String input = InputView.readPlayerName(); - return PlayerParser.parse(input); - }); - Dealer dealer = new Dealer(); - - provideInitCardsPrint(players, dealer); + Users users = retryUntilSuccess(this::createUsers); - hit(players, dealer); + provideInitCardsAndPrint(users); - List users = new ArrayList<>(players); - users.addFirst(dealer); + hit(users); - List gameSummaries = createGameSummaryAndPrint(users); + printHandStatus(users); - createGameResultAndPrint(gameSummaries, users); + printGameResult(users); InputView.closeScanner(); } - private void provideInitCardsPrint(List players, Dealer dealer) { - cardProvider.provideInitCards(players, dealer); - OutputView.printInitCards(players, dealer); + private Users createUsers() { + String input = InputView.readPlayerName(); + return new Users(input); } - private void createGameResultAndPrint(List gameSummaries, List users) { - gameResultCalculator.calculate(gameSummaries); - OutputView.printGameResult(users); + private void provideInitCardsAndPrint(Users users) { + cardProvider.provideInitCards(users); + OutputView.printInitCards(users); } - private List createGameSummaryAndPrint(List users) { - List gameSummaries = new ArrayList<>(); - for (User user : users) { - int totalScore = cardCalculator.totalScore(user.cards()); - boolean bust = cardCalculator.calculateBust(totalScore); - boolean blackjack = cardCalculator.calculateBlackjack(user.cards()); - - GameSummary gameSummary = new GameSummary(user, totalScore, bust, blackjack); - gameSummaries.add(gameSummary); - OutputView.printCardStatus(gameSummary); - } - return gameSummaries; - } + private void hit(Users users) { + List players = users.getPlayers(); + Dealer dealer = users.getDealer(); - public void hit(List players, Dealer dealer) { for (Player player : players) { while (retryUntilSuccess(() -> checkY(player)) && checkAddCard(player)) { cardProvider.provideOneCard(player); @@ -88,24 +56,32 @@ public void hit(List players, Dealer dealer) { } } - while (cardCalculator.totalScore(dealer.cards()) < DEALER_ADD_CARD_STAND) { - OutputView.printDealerHit(); + while (dealer.isHitAvailable()) { cardProvider.provideOneCard(dealer); + OutputView.printDealerHit(); } } - private static boolean checkY(Player player) { + private void printHandStatus(Users users) { + OutputView.printHandStatus(users); + } + + private void printGameResult(Users users) { + PlayersGameResult playersGameResult = users.determineWinner(); + OutputView.printGameResult(playersGameResult, users); + } + + private boolean checkY(Player player) { String input = InputView.readCardAdd(player).trim(); - Validator.validateEmpty(input, ErrorMessage.ERROR_EMPTY_INPUT.getErrorMessage()); - Validator.validateRegrex(Y_N_REGREX, input, ErrorMessage.ERROR_NOT_Y_N_INPUT.getErrorMessage()); - return input.equals("y"); + HitCommand hitCommand = new HitCommand(input); + return hitCommand.isY(); } - boolean checkAddCard(Player player) { - if (cardCalculator.totalScore(player.cards()) >= TWENTY_ONE) { - OutputView.printCantAddCard(); - return false; + private boolean checkAddCard(Player player) { + if (player.isHitAvailable()) { + return true; } - return true; + OutputView.printCantHit(); + return false; } } From 991503c275cce693cc040e9bfcbb99957d6a595c Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 14:47:52 +0900 Subject: [PATCH 43/81] =?UTF-8?q?refactor:=20Map=20=EB=9D=BC=EC=9D=B4?= =?UTF-8?q?=EB=B8=8C=EB=9F=AC=EB=A6=AC=20=EB=A9=94=EC=84=9C=EB=93=9C=20?= =?UTF-8?q?=EA=B5=90=EC=B2=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/Dealer.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/blackjack/model/Dealer.java b/src/main/java/blackjack/model/Dealer.java index 7c7dd62e40b..a9fc9e5f771 100644 --- a/src/main/java/blackjack/model/Dealer.java +++ b/src/main/java/blackjack/model/Dealer.java @@ -15,7 +15,7 @@ public EnumMap getGameResults() { } public void addResult(GameResult gameResult) { - gameResults.put(gameResult, gameResults.getOrDefault(gameResult, 0) + 1); + gameResults.merge(gameResult, 1, Integer::sum); } @Override From d0398d1233c48f95031f978341d3ac3fc55aa609 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 14:56:27 +0900 Subject: [PATCH 44/81] =?UTF-8?q?refactor:=20=ED=8F=B4=EB=8D=94=20?= =?UTF-8?q?=EA=B5=AC=EC=A1=B0=20=EB=B3=80=EA=B2=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../controller/BlackjackController.java | 6 +- .../java/blackjack/model/CardProvider.java | 13 +++- .../java/blackjack/model/GameSummary.java | 4 - src/main/java/blackjack/model/Hand.java | 14 ++-- src/main/java/blackjack/model/HitCommand.java | 4 +- .../blackjack/model/PlayersGameResult.java | 1 + .../java/blackjack/model/{ => card}/Card.java | 2 +- .../java/blackjack/model/{ => card}/Rank.java | 2 +- .../java/blackjack/model/{ => card}/Suit.java | 2 +- .../model/{ => constant}/Constant.java | 2 +- .../model/{ => constant}/ErrorMessage.java | 2 +- .../blackjack/model/{ => user}/Dealer.java | 4 +- .../blackjack/model/{ => user}/Player.java | 4 +- .../java/blackjack/model/{ => user}/User.java | 4 +- .../blackjack/model/{ => user}/UserName.java | 6 +- .../blackjack/model/{ => user}/Users.java | 4 +- .../java/blackjack/util/PlayerParser.java | 2 +- src/main/java/blackjack/view/InputView.java | 2 +- src/main/java/blackjack/view/OutputView.java | 11 ++- .../controller/BlackjackControllerTest.java | 23 +++--- .../blackjack/model/CardCalculatorTest.java | 66 ++++++++-------- .../blackjack/model/CardProviderTest.java | 76 +++++++++---------- .../java/blackjack/util/PlayerParserTest.java | 2 +- 23 files changed, 133 insertions(+), 123 deletions(-) delete mode 100644 src/main/java/blackjack/model/GameSummary.java rename src/main/java/blackjack/model/{ => card}/Card.java (92%) rename src/main/java/blackjack/model/{ => card}/Rank.java (94%) rename src/main/java/blackjack/model/{ => card}/Suit.java (90%) rename src/main/java/blackjack/model/{ => constant}/Constant.java (90%) rename src/main/java/blackjack/model/{ => constant}/ErrorMessage.java (93%) rename src/main/java/blackjack/model/{ => user}/Dealer.java (84%) rename src/main/java/blackjack/model/{ => user}/Player.java (74%) rename src/main/java/blackjack/model/{ => user}/User.java (88%) rename src/main/java/blackjack/model/{ => user}/UserName.java (80%) rename src/main/java/blackjack/model/{ => user}/Users.java (96%) diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index 94eb7a415c3..093dd616f11 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -4,10 +4,10 @@ import blackjack.model.HitCommand; import blackjack.model.CardProvider; -import blackjack.model.Dealer; -import blackjack.model.Player; +import blackjack.model.user.Dealer; +import blackjack.model.user.Player; import blackjack.model.PlayersGameResult; -import blackjack.model.Users; +import blackjack.model.user.Users; import blackjack.view.InputView; import blackjack.view.OutputView; import java.util.List; diff --git a/src/main/java/blackjack/model/CardProvider.java b/src/main/java/blackjack/model/CardProvider.java index 3d2e5fe1a0a..9623dd7dfec 100644 --- a/src/main/java/blackjack/model/CardProvider.java +++ b/src/main/java/blackjack/model/CardProvider.java @@ -1,8 +1,15 @@ package blackjack.model; -import static blackjack.model.Constant.INIT_CARDS_END_IDX; -import static blackjack.model.Constant.INIT_CARDS_START_IDX; - +import static blackjack.model.constant.Constant.INIT_CARDS_END_IDX; +import static blackjack.model.constant.Constant.INIT_CARDS_START_IDX; + +import blackjack.model.card.Card; +import blackjack.model.card.Rank; +import blackjack.model.card.Suit; +import blackjack.model.user.Dealer; +import blackjack.model.user.Player; +import blackjack.model.user.User; +import blackjack.model.user.Users; import java.util.ArrayList; import java.util.Collections; import java.util.LinkedList; diff --git a/src/main/java/blackjack/model/GameSummary.java b/src/main/java/blackjack/model/GameSummary.java deleted file mode 100644 index 5453fe3606f..00000000000 --- a/src/main/java/blackjack/model/GameSummary.java +++ /dev/null @@ -1,4 +0,0 @@ -package blackjack.model; - -public record GameSummary(User user, int totalScore, boolean bust, boolean blackjack) { -} \ No newline at end of file diff --git a/src/main/java/blackjack/model/Hand.java b/src/main/java/blackjack/model/Hand.java index 825909f9fa8..e4bda40e96b 100644 --- a/src/main/java/blackjack/model/Hand.java +++ b/src/main/java/blackjack/model/Hand.java @@ -1,11 +1,13 @@ package blackjack.model; -import static blackjack.model.Constant.ACE_SCORE_ELEVEN; -import static blackjack.model.Constant.ACE_SCORE_ONE; -import static blackjack.model.Constant.INIT_CARDS_END_IDX; -import static blackjack.model.Constant.INIT_CARDS_START_IDX; -import static blackjack.model.Constant.BLACKJACK_SCORE; - +import static blackjack.model.constant.Constant.ACE_SCORE_ELEVEN; +import static blackjack.model.constant.Constant.ACE_SCORE_ONE; +import static blackjack.model.constant.Constant.INIT_CARDS_END_IDX; +import static blackjack.model.constant.Constant.INIT_CARDS_START_IDX; +import static blackjack.model.constant.Constant.BLACKJACK_SCORE; + +import blackjack.model.card.Card; +import blackjack.model.card.Rank; import java.util.ArrayList; import java.util.List; import java.util.Map; diff --git a/src/main/java/blackjack/model/HitCommand.java b/src/main/java/blackjack/model/HitCommand.java index 8f31d6a71ab..f04f008ff93 100644 --- a/src/main/java/blackjack/model/HitCommand.java +++ b/src/main/java/blackjack/model/HitCommand.java @@ -1,7 +1,7 @@ package blackjack.model; -import static blackjack.model.ErrorMessage.ERROR_EMPTY_INPUT; -import static blackjack.model.ErrorMessage.ERROR_NOT_Y_N_INPUT; +import static blackjack.model.constant.ErrorMessage.ERROR_EMPTY_INPUT; +import static blackjack.model.constant.ErrorMessage.ERROR_NOT_Y_N_INPUT; import java.util.regex.Pattern; diff --git a/src/main/java/blackjack/model/PlayersGameResult.java b/src/main/java/blackjack/model/PlayersGameResult.java index c564cf5e3c2..526cd1a1d20 100644 --- a/src/main/java/blackjack/model/PlayersGameResult.java +++ b/src/main/java/blackjack/model/PlayersGameResult.java @@ -1,5 +1,6 @@ package blackjack.model; +import blackjack.model.user.Player; import java.util.Map; public record PlayersGameResult(Map result) { diff --git a/src/main/java/blackjack/model/Card.java b/src/main/java/blackjack/model/card/Card.java similarity index 92% rename from src/main/java/blackjack/model/Card.java rename to src/main/java/blackjack/model/card/Card.java index c127ed760bf..a9293b9cc0c 100644 --- a/src/main/java/blackjack/model/Card.java +++ b/src/main/java/blackjack/model/card/Card.java @@ -1,4 +1,4 @@ -package blackjack.model; +package blackjack.model.card; public class Card { diff --git a/src/main/java/blackjack/model/Rank.java b/src/main/java/blackjack/model/card/Rank.java similarity index 94% rename from src/main/java/blackjack/model/Rank.java rename to src/main/java/blackjack/model/card/Rank.java index 12447254fd1..f0469cd98ab 100644 --- a/src/main/java/blackjack/model/Rank.java +++ b/src/main/java/blackjack/model/card/Rank.java @@ -1,4 +1,4 @@ -package blackjack.model; +package blackjack.model.card; public enum Rank { diff --git a/src/main/java/blackjack/model/Suit.java b/src/main/java/blackjack/model/card/Suit.java similarity index 90% rename from src/main/java/blackjack/model/Suit.java rename to src/main/java/blackjack/model/card/Suit.java index fd20dc7858c..3514549edfd 100644 --- a/src/main/java/blackjack/model/Suit.java +++ b/src/main/java/blackjack/model/card/Suit.java @@ -1,4 +1,4 @@ -package blackjack.model; +package blackjack.model.card; public enum Suit { diff --git a/src/main/java/blackjack/model/Constant.java b/src/main/java/blackjack/model/constant/Constant.java similarity index 90% rename from src/main/java/blackjack/model/Constant.java rename to src/main/java/blackjack/model/constant/Constant.java index 66b9a546f6c..f2389f6895d 100644 --- a/src/main/java/blackjack/model/Constant.java +++ b/src/main/java/blackjack/model/constant/Constant.java @@ -1,4 +1,4 @@ -package blackjack.model; +package blackjack.model.constant; public class Constant { diff --git a/src/main/java/blackjack/model/ErrorMessage.java b/src/main/java/blackjack/model/constant/ErrorMessage.java similarity index 93% rename from src/main/java/blackjack/model/ErrorMessage.java rename to src/main/java/blackjack/model/constant/ErrorMessage.java index 07edd5b5ce0..7aa3f071b21 100644 --- a/src/main/java/blackjack/model/ErrorMessage.java +++ b/src/main/java/blackjack/model/constant/ErrorMessage.java @@ -1,4 +1,4 @@ -package blackjack.model; +package blackjack.model.constant; public enum ErrorMessage { diff --git a/src/main/java/blackjack/model/Dealer.java b/src/main/java/blackjack/model/user/Dealer.java similarity index 84% rename from src/main/java/blackjack/model/Dealer.java rename to src/main/java/blackjack/model/user/Dealer.java index a9fc9e5f771..72c7faa64e2 100644 --- a/src/main/java/blackjack/model/Dealer.java +++ b/src/main/java/blackjack/model/user/Dealer.java @@ -1,5 +1,7 @@ -package blackjack.model; +package blackjack.model.user; +import blackjack.model.constant.Constant; +import blackjack.model.GameResult; import java.util.EnumMap; public class Dealer extends User { diff --git a/src/main/java/blackjack/model/Player.java b/src/main/java/blackjack/model/user/Player.java similarity index 74% rename from src/main/java/blackjack/model/Player.java rename to src/main/java/blackjack/model/user/Player.java index c83019db6d6..56c7825c638 100644 --- a/src/main/java/blackjack/model/Player.java +++ b/src/main/java/blackjack/model/user/Player.java @@ -1,6 +1,8 @@ -package blackjack.model; +package blackjack.model.user; +import blackjack.model.constant.Constant; + public class Player extends User { public Player(String name) { super(name); diff --git a/src/main/java/blackjack/model/User.java b/src/main/java/blackjack/model/user/User.java similarity index 88% rename from src/main/java/blackjack/model/User.java rename to src/main/java/blackjack/model/user/User.java index 713da04cf38..aee3e01c709 100644 --- a/src/main/java/blackjack/model/User.java +++ b/src/main/java/blackjack/model/user/User.java @@ -1,5 +1,7 @@ -package blackjack.model; +package blackjack.model.user; +import blackjack.model.card.Card; +import blackjack.model.Hand; import java.util.List; public abstract class User { diff --git a/src/main/java/blackjack/model/UserName.java b/src/main/java/blackjack/model/user/UserName.java similarity index 80% rename from src/main/java/blackjack/model/UserName.java rename to src/main/java/blackjack/model/user/UserName.java index 1b5b829617e..18512f344a1 100644 --- a/src/main/java/blackjack/model/UserName.java +++ b/src/main/java/blackjack/model/user/UserName.java @@ -1,7 +1,7 @@ -package blackjack.model; +package blackjack.model.user; -import static blackjack.model.ErrorMessage.ERROR_EMPTY_INPUT; -import static blackjack.model.ErrorMessage.ERROR_INVALID_PLAYER_NAME; +import static blackjack.model.constant.ErrorMessage.ERROR_EMPTY_INPUT; +import static blackjack.model.constant.ErrorMessage.ERROR_INVALID_PLAYER_NAME; import java.util.regex.Pattern; diff --git a/src/main/java/blackjack/model/Users.java b/src/main/java/blackjack/model/user/Users.java similarity index 96% rename from src/main/java/blackjack/model/Users.java rename to src/main/java/blackjack/model/user/Users.java index 2dde1360595..d627746d129 100644 --- a/src/main/java/blackjack/model/Users.java +++ b/src/main/java/blackjack/model/user/Users.java @@ -1,5 +1,7 @@ -package blackjack.model; +package blackjack.model.user; +import blackjack.model.GameResult; +import blackjack.model.PlayersGameResult; import blackjack.util.PlayerParser; import java.util.ArrayList; import java.util.HashMap; diff --git a/src/main/java/blackjack/util/PlayerParser.java b/src/main/java/blackjack/util/PlayerParser.java index f05ef01653d..338f3de51c1 100644 --- a/src/main/java/blackjack/util/PlayerParser.java +++ b/src/main/java/blackjack/util/PlayerParser.java @@ -1,6 +1,6 @@ package blackjack.util; -import blackjack.model.Player; +import blackjack.model.user.Player; import java.util.Arrays; import java.util.List; diff --git a/src/main/java/blackjack/view/InputView.java b/src/main/java/blackjack/view/InputView.java index de3226e05d6..577bdde668b 100644 --- a/src/main/java/blackjack/view/InputView.java +++ b/src/main/java/blackjack/view/InputView.java @@ -1,6 +1,6 @@ package blackjack.view; -import blackjack.model.Player; +import blackjack.model.user.Player; import java.util.Scanner; public class InputView { diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index 7465568612d..5fb702f523c 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -1,14 +1,13 @@ package blackjack.view; -import static blackjack.model.Constant.BLACKJACK_SCORE; +import static blackjack.model.constant.Constant.BLACKJACK_SCORE; -import blackjack.model.Card; -import blackjack.model.Dealer; +import blackjack.model.card.Card; +import blackjack.model.user.Dealer; import blackjack.model.GameResult; -import blackjack.model.Player; +import blackjack.model.user.Player; import blackjack.model.PlayersGameResult; -import blackjack.model.User; -import blackjack.model.Users; +import blackjack.model.user.Users; import java.util.EnumMap; import java.util.List; import java.util.Map; diff --git a/src/test/java/blackjack/controller/BlackjackControllerTest.java b/src/test/java/blackjack/controller/BlackjackControllerTest.java index 1cfb979521b..33f157cfec7 100644 --- a/src/test/java/blackjack/controller/BlackjackControllerTest.java +++ b/src/test/java/blackjack/controller/BlackjackControllerTest.java @@ -1,20 +1,17 @@ package blackjack.controller; -import blackjack.model.Card; -import blackjack.model.CardCalculator; +import blackjack.model.card.Card; import blackjack.model.CardProvider; -import blackjack.model.GameResultCalculator; -import blackjack.model.Player; +import blackjack.model.user.Player; +import blackjack.model.card.Rank; +import blackjack.model.card.Suit; import org.assertj.core.api.Assertions; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; class BlackjackControllerTest { private final CardProvider cardProvider = new CardProvider(); - private final CardCalculator cardCalculator = new CardCalculator(); - private final GameResultCalculator gameResultCalculator = new GameResultCalculator(); - private final BlackjackController blackjackController = new BlackjackController(cardProvider, cardCalculator, - gameResultCalculator); + private final BlackjackController blackjackController = new BlackjackController(cardProvider); @Test @@ -22,9 +19,9 @@ class BlackjackControllerTest { void test_checkAddCard_return_false() { Player player = new Player("pobi"); - player.addCard(Card.J_DIA); - player.addCard(Card.Q_CLOVER); - player.addCard(Card.TEN_HEART); + player.addCard(new Card(Rank.J, Suit.DIAMOND)); + player.addCard(new Card(Rank.Q, Suit.CLOVER)); + player.addCard(new Card(Rank.K, Suit.HEART)); Assertions.assertThat(blackjackController.checkAddCard(player)).isFalse(); } @@ -34,8 +31,8 @@ void test_checkAddCard_return_false() { void test_checkAddCard_return_true() { Player player = new Player("pobi"); - player.addCard(Card.J_DIA); - player.addCard(Card.Q_CLOVER); + player.addCard(new Card(Rank.J, Suit.DIAMOND)); + player.addCard(new Card(Rank.Q, Suit.CLOVER)); Assertions.assertThat(blackjackController.checkAddCard(player)).isTrue(); } diff --git a/src/test/java/blackjack/model/CardCalculatorTest.java b/src/test/java/blackjack/model/CardCalculatorTest.java index fff6f9048d9..662d8188b17 100644 --- a/src/test/java/blackjack/model/CardCalculatorTest.java +++ b/src/test/java/blackjack/model/CardCalculatorTest.java @@ -1,33 +1,33 @@ -package blackjack.model; - -import java.util.List; -import org.assertj.core.api.Assertions; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -class CardCalculatorTest { - - @Test - @DisplayName("카드의 총합이 10 이하일 경우 ace 카드의 점수는 11") - void test_getTotalScore_when_ace_is_eleven() { - List aceCards = List.of(Card.A_SPADE); - int totalScore = 10; - CardCalculator cardCalculator = new CardCalculator(); - - int result = cardCalculator.addAceScore(aceCards, totalScore); - - Assertions.assertThat(result).isEqualTo(totalScore + 11); - } - - @Test - @DisplayName("카드의 총합이 11 이상일 경우 ace 카드의 점수는 1") - void test_getTotalScore_when_ace_is_one() { - List aceCards = List.of(Card.A_SPADE); - int totalScore = 11; - CardCalculator cardCalculator = new CardCalculator(); - - int result = cardCalculator.addAceScore(aceCards, totalScore); - - Assertions.assertThat(result).isEqualTo(totalScore + 1); - } -} \ No newline at end of file +//package blackjack.model; +// +//import java.util.List; +//import org.assertj.core.api.Assertions; +//import org.junit.jupiter.api.DisplayName; +//import org.junit.jupiter.api.Test; +// +//class CardCalculatorTest { +// +// @Test +// @DisplayName("카드의 총합이 10 이하일 경우 ace 카드의 점수는 11") +// void test_getTotalScore_when_ace_is_eleven() { +// List aceCards = List.of(Cardx.A_SPADE); +// int totalScore = 10; +// CardCalculator cardCalculator = new CardCalculator(); +// +// int result = cardCalculator.addAceScore(aceCards, totalScore); +// +// Assertions.assertThat(result).isEqualTo(totalScore + 11); +// } +// +// @Test +// @DisplayName("카드의 총합이 11 이상일 경우 ace 카드의 점수는 1") +// void test_getTotalScore_when_ace_is_one() { +// List aceCards = List.of(Cardx.A_SPADE); +// int totalScore = 11; +// CardCalculator cardCalculator = new CardCalculator(); +// +// int result = cardCalculator.addAceScore(aceCards, totalScore); +// +// Assertions.assertThat(result).isEqualTo(totalScore + 1); +// } +//} \ No newline at end of file diff --git a/src/test/java/blackjack/model/CardProviderTest.java b/src/test/java/blackjack/model/CardProviderTest.java index e9f6a2da23f..76396b864b2 100644 --- a/src/test/java/blackjack/model/CardProviderTest.java +++ b/src/test/java/blackjack/model/CardProviderTest.java @@ -1,38 +1,38 @@ -package blackjack.model; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.util.List; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -class CardProviderTest { - - @Test - @DisplayName("딜러 및 플레이어에게 초기 카드 2장 정상 배분") - void test_provide_init_cards() { - CardProvider cardProvider = new CardProvider(); - - List players = List.of(new Player("pobi"), new Player("james")); - Dealer dealer = new Dealer(); - - cardProvider.provideInitCards(players, dealer); - - for (Player player : players) { - assertThat(player.cards().size()).isEqualTo(2); - } - assertThat(dealer.cards().size()).isEqualTo(2); - } - - @Test - @DisplayName("카드 추가 지급 성공") - void test_provide_one_card_success() { - Player player = new Player("pobi"); - CardProvider cardProvider = new CardProvider(); - - cardProvider.provideOneCard(player); - - assertThat(player.cards().size()).isEqualTo(1); - } - -} \ No newline at end of file +//package blackjack.model; +// +//import static org.assertj.core.api.Assertions.assertThat; +// +//import java.util.List; +//import org.junit.jupiter.api.DisplayName; +//import org.junit.jupiter.api.Test; +// +//class CardProviderTest { +// +// @Test +// @DisplayName("딜러 및 플레이어에게 초기 카드 2장 정상 배분") +// void test_provide_init_cards() { +// CardProvider cardProvider = new CardProvider(); +// +// List players = List.of(new Player("pobi"), new Player("james")); +// Dealer dealer = new Dealer(); +// +// cardProvider.provideInitCards(players, dealer); +// +// for (Player player : players) { +// assertThat(player.cards().size()).isEqualTo(2); +// } +// assertThat(dealer.cards().size()).isEqualTo(2); +// } +// +// @Test +// @DisplayName("카드 추가 지급 성공") +// void test_provide_one_card_success() { +// Player player = new Player("pobi"); +// CardProvider cardProvider = new CardProvider(); +// +// cardProvider.provideOneCard(player); +// +// assertThat(player.cards().size()).isEqualTo(1); +// } +// +//} \ No newline at end of file diff --git a/src/test/java/blackjack/util/PlayerParserTest.java b/src/test/java/blackjack/util/PlayerParserTest.java index f46f177f588..3ea07163d2e 100644 --- a/src/test/java/blackjack/util/PlayerParserTest.java +++ b/src/test/java/blackjack/util/PlayerParserTest.java @@ -3,7 +3,7 @@ import static org.assertj.core.api.Assertions.assertThat; import static org.assertj.core.api.Assertions.assertThatThrownBy; -import blackjack.model.Player; +import blackjack.model.user.Player; import java.util.List; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; From ef6e0d274dd5769c3d448460cecd15349c09632a Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 15:14:56 +0900 Subject: [PATCH 45/81] =?UTF-8?q?refactor:=20=EA=B3=B5=EB=B0=B1=20?= =?UTF-8?q?=EA=B2=80=EC=A6=9D=20=EB=A9=94=EC=84=9C=EB=93=9C=20=EC=88=98?= =?UTF-8?q?=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/HitCommand.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/blackjack/model/HitCommand.java b/src/main/java/blackjack/model/HitCommand.java index f04f008ff93..48dc2a392da 100644 --- a/src/main/java/blackjack/model/HitCommand.java +++ b/src/main/java/blackjack/model/HitCommand.java @@ -22,7 +22,7 @@ public boolean isY() { } private void validateEmpty(String command) { - if (command.isEmpty()) { + if (command.isBlank()) { throw new IllegalArgumentException(ERROR_EMPTY_INPUT.getErrorMessage()); } } From a63f529e4ef288a5d4e5f44f1c7d1a7cfac35829 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 15:17:37 +0900 Subject: [PATCH 46/81] =?UTF-8?q?refactor:=20=EB=AF=B8=EC=82=AC=EC=9A=A9?= =?UTF-8?q?=20=EB=A9=94=EC=84=9C=EB=93=9C=20=EC=82=AD=EC=A0=9C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/Hand.java | 4 ---- 1 file changed, 4 deletions(-) diff --git a/src/main/java/blackjack/model/Hand.java b/src/main/java/blackjack/model/Hand.java index e4bda40e96b..0513828dd21 100644 --- a/src/main/java/blackjack/model/Hand.java +++ b/src/main/java/blackjack/model/Hand.java @@ -38,10 +38,6 @@ public boolean isBust() { return totalScore(cards) > BLACKJACK_SCORE; } - public boolean isHitAvailable() { - return totalScore(cards) >= BLACKJACK_SCORE; - } - public int calculateTotalScore() { return totalScore(cards); } From df9803a7de94caf874c0d51638d0f82dda5cb361 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 15:36:27 +0900 Subject: [PATCH 47/81] =?UTF-8?q?refactor:=20=EA=B3=B5=EB=B0=B1=20?= =?UTF-8?q?=EA=B2=80=EC=A6=9D=20=EB=A9=94=EC=84=9C=EB=93=9C=20=EC=88=98?= =?UTF-8?q?=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../model/user/{UserName.java => Username.java} | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) rename src/main/java/blackjack/model/user/{UserName.java => Username.java} (67%) diff --git a/src/main/java/blackjack/model/user/UserName.java b/src/main/java/blackjack/model/user/Username.java similarity index 67% rename from src/main/java/blackjack/model/user/UserName.java rename to src/main/java/blackjack/model/user/Username.java index 18512f344a1..accf14b1941 100644 --- a/src/main/java/blackjack/model/user/UserName.java +++ b/src/main/java/blackjack/model/user/Username.java @@ -5,15 +5,15 @@ import java.util.regex.Pattern; -public class UserName { +public class Username { - private static final String PLAYER_NAME_REGREX = "^[a-zA-Z가-힣]*$"; + private static final String PLAYER_NAME_REGEX = "^[a-zA-Z가-힣]*$"; private final String name; - public UserName(String name) { + public Username(String name) { validateEmpty(name); - validateRegrex(name); + validateRegex(name); this.name = name; } @@ -22,13 +22,13 @@ public String getName() { } private void validateEmpty(String name) { - if (name.isEmpty()) { + if (name.isBlank()) { throw new IllegalArgumentException(ERROR_EMPTY_INPUT.getErrorMessage()); } } - public static void validateRegrex(String name) { - if (!Pattern.matches(PLAYER_NAME_REGREX, name)) { + public static void validateRegex(String name) { + if (!Pattern.matches(PLAYER_NAME_REGEX, name)) { throw new IllegalArgumentException(ERROR_INVALID_PLAYER_NAME.getErrorMessage()); } } From b2d2d36bf79a20b50737f11dfa1c968c1e745999 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 15:36:54 +0900 Subject: [PATCH 48/81] =?UTF-8?q?refactor:=20UserName=20->=20Username=20?= =?UTF-8?q?=ED=81=B4=EB=9E=98=EC=8A=A4=EB=AA=85=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/user/User.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/blackjack/model/user/User.java b/src/main/java/blackjack/model/user/User.java index aee3e01c709..4bff4366341 100644 --- a/src/main/java/blackjack/model/user/User.java +++ b/src/main/java/blackjack/model/user/User.java @@ -6,11 +6,11 @@ public abstract class User { - private final UserName name; + private final Username name; private final Hand hand; public User(String name) { - this.name = new UserName(name); + this.name = new Username(name); this.hand = new Hand(); } From 9ec41b60dbfbd0246336779f8e3f44a69e9bb63b Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 16:03:29 +0900 Subject: [PATCH 49/81] =?UTF-8?q?test:=20=EB=8B=A8=EC=9C=84=20=ED=85=8C?= =?UTF-8?q?=EC=8A=A4=ED=8A=B8=20=EC=88=98=EC=A0=95=20=EB=B0=8F=20=EC=B6=94?= =?UTF-8?q?=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../controller/BlackjackControllerTest.java | 39 --------- .../blackjack/model/CardCalculatorTest.java | 33 -------- .../blackjack/model/CardProviderTest.java | 80 ++++++++++--------- src/test/java/blackjack/model/HandTest.java | 62 ++++++++++++++ .../java/blackjack/model/HitCommandTest.java | 42 ++++++++++ .../java/blackjack/model/user/DealerTest.java | 35 ++++++++ .../java/blackjack/model/user/PlayerTest.java | 35 ++++++++ .../blackjack/model/user/UsernameTest.java | 41 ++++++++++ .../java/blackjack/util/PlayerParserTest.java | 20 ----- 9 files changed, 257 insertions(+), 130 deletions(-) delete mode 100644 src/test/java/blackjack/controller/BlackjackControllerTest.java delete mode 100644 src/test/java/blackjack/model/CardCalculatorTest.java create mode 100644 src/test/java/blackjack/model/HandTest.java create mode 100644 src/test/java/blackjack/model/HitCommandTest.java create mode 100644 src/test/java/blackjack/model/user/DealerTest.java create mode 100644 src/test/java/blackjack/model/user/PlayerTest.java create mode 100644 src/test/java/blackjack/model/user/UsernameTest.java diff --git a/src/test/java/blackjack/controller/BlackjackControllerTest.java b/src/test/java/blackjack/controller/BlackjackControllerTest.java deleted file mode 100644 index 33f157cfec7..00000000000 --- a/src/test/java/blackjack/controller/BlackjackControllerTest.java +++ /dev/null @@ -1,39 +0,0 @@ -package blackjack.controller; - -import blackjack.model.card.Card; -import blackjack.model.CardProvider; -import blackjack.model.user.Player; -import blackjack.model.card.Rank; -import blackjack.model.card.Suit; -import org.assertj.core.api.Assertions; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -class BlackjackControllerTest { - private final CardProvider cardProvider = new CardProvider(); - private final BlackjackController blackjackController = new BlackjackController(cardProvider); - - - @Test - @DisplayName("카드의 합이 21이상인 경우 카드 추가 지급 불가 ( false 반환 )") - void test_checkAddCard_return_false() { - - Player player = new Player("pobi"); - player.addCard(new Card(Rank.J, Suit.DIAMOND)); - player.addCard(new Card(Rank.Q, Suit.CLOVER)); - player.addCard(new Card(Rank.K, Suit.HEART)); - - Assertions.assertThat(blackjackController.checkAddCard(player)).isFalse(); - } - - @Test - @DisplayName("카드의 합이 21 이하인 경우 카드 추가 지급 가능 ( true 반환 )") - void test_checkAddCard_return_true() { - - Player player = new Player("pobi"); - player.addCard(new Card(Rank.J, Suit.DIAMOND)); - player.addCard(new Card(Rank.Q, Suit.CLOVER)); - - Assertions.assertThat(blackjackController.checkAddCard(player)).isTrue(); - } -} \ No newline at end of file diff --git a/src/test/java/blackjack/model/CardCalculatorTest.java b/src/test/java/blackjack/model/CardCalculatorTest.java deleted file mode 100644 index 662d8188b17..00000000000 --- a/src/test/java/blackjack/model/CardCalculatorTest.java +++ /dev/null @@ -1,33 +0,0 @@ -//package blackjack.model; -// -//import java.util.List; -//import org.assertj.core.api.Assertions; -//import org.junit.jupiter.api.DisplayName; -//import org.junit.jupiter.api.Test; -// -//class CardCalculatorTest { -// -// @Test -// @DisplayName("카드의 총합이 10 이하일 경우 ace 카드의 점수는 11") -// void test_getTotalScore_when_ace_is_eleven() { -// List aceCards = List.of(Cardx.A_SPADE); -// int totalScore = 10; -// CardCalculator cardCalculator = new CardCalculator(); -// -// int result = cardCalculator.addAceScore(aceCards, totalScore); -// -// Assertions.assertThat(result).isEqualTo(totalScore + 11); -// } -// -// @Test -// @DisplayName("카드의 총합이 11 이상일 경우 ace 카드의 점수는 1") -// void test_getTotalScore_when_ace_is_one() { -// List aceCards = List.of(Cardx.A_SPADE); -// int totalScore = 11; -// CardCalculator cardCalculator = new CardCalculator(); -// -// int result = cardCalculator.addAceScore(aceCards, totalScore); -// -// Assertions.assertThat(result).isEqualTo(totalScore + 1); -// } -//} \ No newline at end of file diff --git a/src/test/java/blackjack/model/CardProviderTest.java b/src/test/java/blackjack/model/CardProviderTest.java index 76396b864b2..a84e53da155 100644 --- a/src/test/java/blackjack/model/CardProviderTest.java +++ b/src/test/java/blackjack/model/CardProviderTest.java @@ -1,38 +1,42 @@ -//package blackjack.model; -// -//import static org.assertj.core.api.Assertions.assertThat; -// -//import java.util.List; -//import org.junit.jupiter.api.DisplayName; -//import org.junit.jupiter.api.Test; -// -//class CardProviderTest { -// -// @Test -// @DisplayName("딜러 및 플레이어에게 초기 카드 2장 정상 배분") -// void test_provide_init_cards() { -// CardProvider cardProvider = new CardProvider(); -// -// List players = List.of(new Player("pobi"), new Player("james")); -// Dealer dealer = new Dealer(); -// -// cardProvider.provideInitCards(players, dealer); -// -// for (Player player : players) { -// assertThat(player.cards().size()).isEqualTo(2); -// } -// assertThat(dealer.cards().size()).isEqualTo(2); -// } -// -// @Test -// @DisplayName("카드 추가 지급 성공") -// void test_provide_one_card_success() { -// Player player = new Player("pobi"); -// CardProvider cardProvider = new CardProvider(); -// -// cardProvider.provideOneCard(player); -// -// assertThat(player.cards().size()).isEqualTo(1); -// } -// -//} \ No newline at end of file +package blackjack.model; + +import static org.assertj.core.api.Assertions.assertThat; + +import blackjack.model.user.Dealer; +import blackjack.model.user.Player; +import blackjack.model.user.Users; +import java.util.List; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +class CardProviderTest { + + @Test + @DisplayName("딜러 및 플레이어에게 초기 카드 2장 정상 배분") + void test_provide_init_cards() { + CardProvider cardProvider = new CardProvider(); + + List players = List.of(new Player("pobi"), new Player("james")); + Dealer dealer = new Dealer(); + Users users = new Users(players, dealer); + + cardProvider.provideInitCards(users); + + for (Player player : players) { + assertThat(player.cards().size()).isEqualTo(2); + } + assertThat(dealer.cards().size()).isEqualTo(2); + } + + @Test + @DisplayName("카드 추가 지급 성공") + void test_provide_one_card_success() { + Player player = new Player("pobi"); + CardProvider cardProvider = new CardProvider(); + + cardProvider.provideOneCard(player); + + assertThat(player.cards().size()).isEqualTo(1); + } + +} \ No newline at end of file diff --git a/src/test/java/blackjack/model/HandTest.java b/src/test/java/blackjack/model/HandTest.java new file mode 100644 index 00000000000..5c4889b4ab5 --- /dev/null +++ b/src/test/java/blackjack/model/HandTest.java @@ -0,0 +1,62 @@ +package blackjack.model; + +import static org.assertj.core.api.Assertions.assertThat; + +import blackjack.model.card.Card; +import blackjack.model.card.Rank; +import blackjack.model.card.Suit; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +class HandTest { + + @Test + @DisplayName("Hand가 블랙잭일 경우 true 반환") + void isBlackjack_return_true() { + //given + Hand hand = new Hand(); + hand.addCard(new Card(Rank.J, Suit.DIAMOND)); + hand.addCard(new Card(Rank.ACE, Suit.DIAMOND)); + + //when & then + assertThat(hand.isBlackjack()).isTrue(); + } + + @Test + @DisplayName("Hand가 블랙잭이 아닐 경우 false 반환") + void isBlackjack_return_false() { + //given + Hand hand = new Hand(); + hand.addCard(new Card(Rank.J, Suit.DIAMOND)); + hand.addCard(new Card(Rank.K, Suit.DIAMOND)); + + //when & then + assertThat(hand.isBlackjack()).isFalse(); + } + + @Test + @DisplayName("Hand가 버스트일 경우 true 반환") + void isBust_return_true() { + //given + Hand hand = new Hand(); + hand.addCard(new Card(Rank.J, Suit.DIAMOND)); + hand.addCard(new Card(Rank.Q, Suit.DIAMOND)); + hand.addCard(new Card(Rank.TWO, Suit.DIAMOND)); + + //when & then + assertThat(hand.isBust()).isTrue(); + } + + @Test + @DisplayName("Hand가 버스트가 아닐 경우 false 반환") + void isBust_return_false() { + //given + Hand hand = new Hand(); + hand.addCard(new Card(Rank.J, Suit.DIAMOND)); + hand.addCard(new Card(Rank.Q, Suit.DIAMOND)); + hand.addCard(new Card(Rank.ACE, Suit.DIAMOND)); + + //when & then + assertThat(hand.isBust()).isFalse(); + } +} \ No newline at end of file diff --git a/src/test/java/blackjack/model/HitCommandTest.java b/src/test/java/blackjack/model/HitCommandTest.java new file mode 100644 index 00000000000..4350d6a5a89 --- /dev/null +++ b/src/test/java/blackjack/model/HitCommandTest.java @@ -0,0 +1,42 @@ +package blackjack.model; + +import static blackjack.model.constant.ErrorMessage.ERROR_EMPTY_INPUT; +import static blackjack.model.constant.ErrorMessage.ERROR_NOT_Y_N_INPUT; +import static org.assertj.core.api.Assertions.assertThatThrownBy; +import static org.junit.jupiter.api.Assertions.assertDoesNotThrow; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.ValueSource; + +class HitCommandTest { + + @ParameterizedTest + @ValueSource(strings = {"y", "Y", "n", "N"}) + @DisplayName("HitCommand 정상 생성") + void create_hitCommand_success(String hitCommand) { + //when & then + assertDoesNotThrow(() -> new HitCommand(hitCommand)); + } + + + @ParameterizedTest + @ValueSource(strings = {"", " "}) + @DisplayName("공백이 입력될 경우 예외 발생") + void create_hitCommand_fail_when_empty_input(String emptyInput) { + //when & then + assertThatThrownBy(() -> new HitCommand(emptyInput)) + .isInstanceOf(IllegalArgumentException.class) + .hasMessage(ERROR_EMPTY_INPUT.getErrorMessage()); + } + + @ParameterizedTest + @ValueSource(strings = {"ad", "y*"}) + @DisplayName("정해진 입력 외의 문자열을 입력할 경우 예외 발생") + void create_hitCommand_fail_when_invalid_input(String invalidInput) { + //when & then + assertThatThrownBy(() -> new HitCommand(invalidInput)) + .isInstanceOf(IllegalArgumentException.class) + .hasMessage(ERROR_NOT_Y_N_INPUT.getErrorMessage()); + } +} \ No newline at end of file diff --git a/src/test/java/blackjack/model/user/DealerTest.java b/src/test/java/blackjack/model/user/DealerTest.java new file mode 100644 index 00000000000..a79c0261174 --- /dev/null +++ b/src/test/java/blackjack/model/user/DealerTest.java @@ -0,0 +1,35 @@ +package blackjack.model.user; + +import blackjack.model.card.Card; +import blackjack.model.card.Rank; +import blackjack.model.card.Suit; +import org.assertj.core.api.Assertions; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +class DealerTest { + + @Test + @DisplayName("딜러 핸드의 합계가 17 미만인 경우 카드 추가 지급 가능 (true 반환)") + void isHitAvailable_return_true() { + //given + Dealer dealer = new Dealer(); + dealer.addCard(new Card(Rank.K, Suit.DIAMOND)); + dealer.addCard(new Card(Rank.SIX, Suit.DIAMOND)); + + //when & then + Assertions.assertThat(dealer.isHitAvailable()).isTrue(); + } + + @Test + @DisplayName("딜러 핸드의 합계가 17 이상인 경우 카드 추가 지급 불가 (false 반환)") + void isHitAvailable_return_false() { + //given + blackjack.model.user.Dealer dealer = new Dealer(); + dealer.addCard(new Card(Rank.K, Suit.DIAMOND)); + dealer.addCard(new Card(Rank.SEVEN, Suit.DIAMOND)); + + //when & then + Assertions.assertThat(dealer.isHitAvailable()).isFalse(); + } +} \ No newline at end of file diff --git a/src/test/java/blackjack/model/user/PlayerTest.java b/src/test/java/blackjack/model/user/PlayerTest.java new file mode 100644 index 00000000000..12f4157428f --- /dev/null +++ b/src/test/java/blackjack/model/user/PlayerTest.java @@ -0,0 +1,35 @@ +package blackjack.model.user; + +import blackjack.model.card.Card; +import blackjack.model.card.Rank; +import blackjack.model.card.Suit; +import org.assertj.core.api.Assertions; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +class PlayerTest { + + @Test + @DisplayName("플레이어 핸드의 합계가 21 미만인 경우 카드 추가 지급 가능 (true 반환)") + void isHitAvailable_return_true() { + //given + Player player = new Player("pobi"); + player.addCard(new Card(Rank.K, Suit.DIAMOND)); + player.addCard(new Card(Rank.J, Suit.DIAMOND)); + + //when & then + Assertions.assertThat(player.isHitAvailable()).isTrue(); + } + + @Test + @DisplayName("플레이어 핸드의 합계가 21 이상인 경우 카드 추가 지급 불가 (false 반환)") + void isHitAvailable_return_false() { + //given + Player player = new Player("pobi"); + player.addCard(new Card(Rank.K, Suit.DIAMOND)); + player.addCard(new Card(Rank.ACE, Suit.DIAMOND)); + + //when & then + Assertions.assertThat(player.isHitAvailable()).isFalse(); + } +} \ No newline at end of file diff --git a/src/test/java/blackjack/model/user/UsernameTest.java b/src/test/java/blackjack/model/user/UsernameTest.java new file mode 100644 index 00000000000..0473f81c347 --- /dev/null +++ b/src/test/java/blackjack/model/user/UsernameTest.java @@ -0,0 +1,41 @@ +package blackjack.model.user; + +import static blackjack.model.constant.ErrorMessage.ERROR_EMPTY_INPUT; +import static blackjack.model.constant.ErrorMessage.ERROR_INVALID_PLAYER_NAME; +import static org.assertj.core.api.Assertions.assertThatThrownBy; +import static org.junit.jupiter.api.Assertions.assertDoesNotThrow; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.ValueSource; + +class UsernameTest { + + @ParameterizedTest + @ValueSource(strings = {"pobi", "jason"}) + @DisplayName("Username 정상 생성") + void create_username_success(String username) { + //when & then + assertDoesNotThrow(() -> new Username(username)); + } + + @ParameterizedTest + @ValueSource(strings = {"", " "}) + @DisplayName("이름이 공백인 경우 예외 발생") + void create_username_fail_when_empty_name(String emptyName) { + //when & then + assertThatThrownBy(() -> new Username(emptyName)) + .isInstanceOf(IllegalArgumentException.class) + .hasMessage(ERROR_EMPTY_INPUT.getErrorMessage()); + } + + @ParameterizedTest + @ValueSource(strings = {"pobi!", "jason1"}) + @DisplayName("이름에 영어와 한글 외의 문자가 존재할 경우 예외 발생") + void create_username_fail_when_invalid_name(String invalidName) { + //when & then + assertThatThrownBy(() -> new Username(invalidName)) + .isInstanceOf(IllegalArgumentException.class) + .hasMessage(ERROR_INVALID_PLAYER_NAME.getErrorMessage()); + } +} \ No newline at end of file diff --git a/src/test/java/blackjack/util/PlayerParserTest.java b/src/test/java/blackjack/util/PlayerParserTest.java index 3ea07163d2e..8ea16048d30 100644 --- a/src/test/java/blackjack/util/PlayerParserTest.java +++ b/src/test/java/blackjack/util/PlayerParserTest.java @@ -1,14 +1,11 @@ package blackjack.util; import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; import blackjack.model.user.Player; import java.util.List; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.ValueSource; class PlayerParserTest { @@ -24,21 +21,4 @@ void test_parse_success() { .extracting("name") .contains("pobi", "james"); } - - @Test - @DisplayName("플레이어의 이름에 영어와 한글이 아닌 문자가 존재하는 경우 예외 발생") - void test_parse_fail_when_invalid_name() { - String invalidInput = "pobi,james*"; - - assertThatThrownBy(() -> PlayerParser.parse(invalidInput)) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @ValueSource(strings = {"", " ", " , , "}) - @DisplayName("플레이어의 이름이 공백인 경우 예외 발생") - void test_parse_fail_when_name_is_null(String emptyName) { - assertThatThrownBy(() -> PlayerParser.parse(emptyName)) - .isInstanceOf(IllegalArgumentException.class); - } } \ No newline at end of file From e9ee2f0a18689d0ad0aa3ecfb561585f58bc2b3a Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 16:08:11 +0900 Subject: [PATCH 50/81] =?UTF-8?q?refactor:=20=ED=8F=B4=EB=8D=94=20?= =?UTF-8?q?=EA=B5=AC=EC=A1=B0=20=EB=B3=80=EA=B2=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/Application.java | 2 +- src/main/java/blackjack/controller/BlackjackController.java | 6 +++--- src/main/java/blackjack/model/{ => card}/CardProvider.java | 5 +---- src/main/java/blackjack/model/{ => card}/Hand.java | 4 +--- src/main/java/blackjack/model/{ => card}/HitCommand.java | 2 +- .../java/blackjack/model/{ => gameresult}/GameResult.java | 2 +- .../blackjack/model/{ => gameresult}/PlayersGameResult.java | 2 +- src/main/java/blackjack/model/user/Dealer.java | 2 +- .../java/blackjack/{util => model/user}/PlayerParser.java | 3 +-- src/main/java/blackjack/model/user/User.java | 2 +- src/main/java/blackjack/model/user/Users.java | 5 ++--- src/main/java/blackjack/view/OutputView.java | 4 ++-- src/test/java/blackjack/model/CardProviderTest.java | 1 + src/test/java/blackjack/model/HandTest.java | 1 + src/test/java/blackjack/model/HitCommandTest.java | 1 + src/test/java/blackjack/util/PlayerParserTest.java | 1 + 16 files changed, 20 insertions(+), 23 deletions(-) rename src/main/java/blackjack/model/{ => card}/CardProvider.java (91%) rename src/main/java/blackjack/model/{ => card}/Hand.java (95%) rename src/main/java/blackjack/model/{ => card}/HitCommand.java (96%) rename src/main/java/blackjack/model/{ => gameresult}/GameResult.java (87%) rename src/main/java/blackjack/model/{ => gameresult}/PlayersGameResult.java (78%) rename src/main/java/blackjack/{util => model/user}/PlayerParser.java (82%) diff --git a/src/main/java/blackjack/Application.java b/src/main/java/blackjack/Application.java index d6e1aebdee6..0d4617c5165 100644 --- a/src/main/java/blackjack/Application.java +++ b/src/main/java/blackjack/Application.java @@ -1,7 +1,7 @@ package blackjack; import blackjack.controller.BlackjackController; -import blackjack.model.CardProvider; +import blackjack.model.card.CardProvider; public class Application { diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index 093dd616f11..03cde5fe19d 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -2,11 +2,11 @@ import static blackjack.util.ExceptionHandler.retryUntilSuccess; -import blackjack.model.HitCommand; -import blackjack.model.CardProvider; +import blackjack.model.card.HitCommand; +import blackjack.model.card.CardProvider; import blackjack.model.user.Dealer; import blackjack.model.user.Player; -import blackjack.model.PlayersGameResult; +import blackjack.model.gameresult.PlayersGameResult; import blackjack.model.user.Users; import blackjack.view.InputView; import blackjack.view.OutputView; diff --git a/src/main/java/blackjack/model/CardProvider.java b/src/main/java/blackjack/model/card/CardProvider.java similarity index 91% rename from src/main/java/blackjack/model/CardProvider.java rename to src/main/java/blackjack/model/card/CardProvider.java index 9623dd7dfec..78ecc6bbd14 100644 --- a/src/main/java/blackjack/model/CardProvider.java +++ b/src/main/java/blackjack/model/card/CardProvider.java @@ -1,11 +1,8 @@ -package blackjack.model; +package blackjack.model.card; import static blackjack.model.constant.Constant.INIT_CARDS_END_IDX; import static blackjack.model.constant.Constant.INIT_CARDS_START_IDX; -import blackjack.model.card.Card; -import blackjack.model.card.Rank; -import blackjack.model.card.Suit; import blackjack.model.user.Dealer; import blackjack.model.user.Player; import blackjack.model.user.User; diff --git a/src/main/java/blackjack/model/Hand.java b/src/main/java/blackjack/model/card/Hand.java similarity index 95% rename from src/main/java/blackjack/model/Hand.java rename to src/main/java/blackjack/model/card/Hand.java index 0513828dd21..e5df390ce82 100644 --- a/src/main/java/blackjack/model/Hand.java +++ b/src/main/java/blackjack/model/card/Hand.java @@ -1,4 +1,4 @@ -package blackjack.model; +package blackjack.model.card; import static blackjack.model.constant.Constant.ACE_SCORE_ELEVEN; import static blackjack.model.constant.Constant.ACE_SCORE_ONE; @@ -6,8 +6,6 @@ import static blackjack.model.constant.Constant.INIT_CARDS_START_IDX; import static blackjack.model.constant.Constant.BLACKJACK_SCORE; -import blackjack.model.card.Card; -import blackjack.model.card.Rank; import java.util.ArrayList; import java.util.List; import java.util.Map; diff --git a/src/main/java/blackjack/model/HitCommand.java b/src/main/java/blackjack/model/card/HitCommand.java similarity index 96% rename from src/main/java/blackjack/model/HitCommand.java rename to src/main/java/blackjack/model/card/HitCommand.java index 48dc2a392da..66ba59fff6d 100644 --- a/src/main/java/blackjack/model/HitCommand.java +++ b/src/main/java/blackjack/model/card/HitCommand.java @@ -1,4 +1,4 @@ -package blackjack.model; +package blackjack.model.card; import static blackjack.model.constant.ErrorMessage.ERROR_EMPTY_INPUT; import static blackjack.model.constant.ErrorMessage.ERROR_NOT_Y_N_INPUT; diff --git a/src/main/java/blackjack/model/GameResult.java b/src/main/java/blackjack/model/gameresult/GameResult.java similarity index 87% rename from src/main/java/blackjack/model/GameResult.java rename to src/main/java/blackjack/model/gameresult/GameResult.java index b4dd6b86f20..ce9e77c968b 100644 --- a/src/main/java/blackjack/model/GameResult.java +++ b/src/main/java/blackjack/model/gameresult/GameResult.java @@ -1,4 +1,4 @@ -package blackjack.model; +package blackjack.model.gameresult; public enum GameResult { diff --git a/src/main/java/blackjack/model/PlayersGameResult.java b/src/main/java/blackjack/model/gameresult/PlayersGameResult.java similarity index 78% rename from src/main/java/blackjack/model/PlayersGameResult.java rename to src/main/java/blackjack/model/gameresult/PlayersGameResult.java index 526cd1a1d20..6440361a6a7 100644 --- a/src/main/java/blackjack/model/PlayersGameResult.java +++ b/src/main/java/blackjack/model/gameresult/PlayersGameResult.java @@ -1,4 +1,4 @@ -package blackjack.model; +package blackjack.model.gameresult; import blackjack.model.user.Player; import java.util.Map; diff --git a/src/main/java/blackjack/model/user/Dealer.java b/src/main/java/blackjack/model/user/Dealer.java index 72c7faa64e2..af688a7ebe6 100644 --- a/src/main/java/blackjack/model/user/Dealer.java +++ b/src/main/java/blackjack/model/user/Dealer.java @@ -1,7 +1,7 @@ package blackjack.model.user; import blackjack.model.constant.Constant; -import blackjack.model.GameResult; +import blackjack.model.gameresult.GameResult; import java.util.EnumMap; public class Dealer extends User { diff --git a/src/main/java/blackjack/util/PlayerParser.java b/src/main/java/blackjack/model/user/PlayerParser.java similarity index 82% rename from src/main/java/blackjack/util/PlayerParser.java rename to src/main/java/blackjack/model/user/PlayerParser.java index 338f3de51c1..114ec437016 100644 --- a/src/main/java/blackjack/util/PlayerParser.java +++ b/src/main/java/blackjack/model/user/PlayerParser.java @@ -1,6 +1,5 @@ -package blackjack.util; +package blackjack.model.user; -import blackjack.model.user.Player; import java.util.Arrays; import java.util.List; diff --git a/src/main/java/blackjack/model/user/User.java b/src/main/java/blackjack/model/user/User.java index 4bff4366341..6780d34b652 100644 --- a/src/main/java/blackjack/model/user/User.java +++ b/src/main/java/blackjack/model/user/User.java @@ -1,7 +1,7 @@ package blackjack.model.user; import blackjack.model.card.Card; -import blackjack.model.Hand; +import blackjack.model.card.Hand; import java.util.List; public abstract class User { diff --git a/src/main/java/blackjack/model/user/Users.java b/src/main/java/blackjack/model/user/Users.java index d627746d129..4a00889229e 100644 --- a/src/main/java/blackjack/model/user/Users.java +++ b/src/main/java/blackjack/model/user/Users.java @@ -1,8 +1,7 @@ package blackjack.model.user; -import blackjack.model.GameResult; -import blackjack.model.PlayersGameResult; -import blackjack.util.PlayerParser; +import blackjack.model.gameresult.GameResult; +import blackjack.model.gameresult.PlayersGameResult; import java.util.ArrayList; import java.util.HashMap; import java.util.List; diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index 5fb702f523c..87d3e7a6fe1 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -4,9 +4,9 @@ import blackjack.model.card.Card; import blackjack.model.user.Dealer; -import blackjack.model.GameResult; +import blackjack.model.gameresult.GameResult; import blackjack.model.user.Player; -import blackjack.model.PlayersGameResult; +import blackjack.model.gameresult.PlayersGameResult; import blackjack.model.user.Users; import java.util.EnumMap; import java.util.List; diff --git a/src/test/java/blackjack/model/CardProviderTest.java b/src/test/java/blackjack/model/CardProviderTest.java index a84e53da155..6f086bf4530 100644 --- a/src/test/java/blackjack/model/CardProviderTest.java +++ b/src/test/java/blackjack/model/CardProviderTest.java @@ -2,6 +2,7 @@ import static org.assertj.core.api.Assertions.assertThat; +import blackjack.model.card.CardProvider; import blackjack.model.user.Dealer; import blackjack.model.user.Player; import blackjack.model.user.Users; diff --git a/src/test/java/blackjack/model/HandTest.java b/src/test/java/blackjack/model/HandTest.java index 5c4889b4ab5..0fa5ef4c795 100644 --- a/src/test/java/blackjack/model/HandTest.java +++ b/src/test/java/blackjack/model/HandTest.java @@ -3,6 +3,7 @@ import static org.assertj.core.api.Assertions.assertThat; import blackjack.model.card.Card; +import blackjack.model.card.Hand; import blackjack.model.card.Rank; import blackjack.model.card.Suit; import org.junit.jupiter.api.DisplayName; diff --git a/src/test/java/blackjack/model/HitCommandTest.java b/src/test/java/blackjack/model/HitCommandTest.java index 4350d6a5a89..930073a4ddd 100644 --- a/src/test/java/blackjack/model/HitCommandTest.java +++ b/src/test/java/blackjack/model/HitCommandTest.java @@ -5,6 +5,7 @@ import static org.assertj.core.api.Assertions.assertThatThrownBy; import static org.junit.jupiter.api.Assertions.assertDoesNotThrow; +import blackjack.model.card.HitCommand; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.ValueSource; diff --git a/src/test/java/blackjack/util/PlayerParserTest.java b/src/test/java/blackjack/util/PlayerParserTest.java index 8ea16048d30..61d1977162e 100644 --- a/src/test/java/blackjack/util/PlayerParserTest.java +++ b/src/test/java/blackjack/util/PlayerParserTest.java @@ -3,6 +3,7 @@ import static org.assertj.core.api.Assertions.assertThat; import blackjack.model.user.Player; +import blackjack.model.user.PlayerParser; import java.util.List; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; From 05a9504cc3cf9488287fa668137a904efc798741 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 16:09:57 +0900 Subject: [PATCH 51/81] =?UTF-8?q?refactor:=20=EA=B2=80=EC=A6=9D=20?= =?UTF-8?q?=EB=A9=94=EC=84=9C=EB=93=9C=20=EC=A0=91=EA=B7=BC=20=EC=A0=9C?= =?UTF-8?q?=EC=96=B4=EC=9E=90=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/user/Username.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/blackjack/model/user/Username.java b/src/main/java/blackjack/model/user/Username.java index accf14b1941..f429dfb5412 100644 --- a/src/main/java/blackjack/model/user/Username.java +++ b/src/main/java/blackjack/model/user/Username.java @@ -27,7 +27,7 @@ private void validateEmpty(String name) { } } - public static void validateRegex(String name) { + private void validateRegex(String name) { if (!Pattern.matches(PLAYER_NAME_REGEX, name)) { throw new IllegalArgumentException(ERROR_INVALID_PLAYER_NAME.getErrorMessage()); } From f397b1cf1b1e23a2c67f3b94376b7130a189ddb0 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Tue, 10 Mar 2026 16:55:40 +0900 Subject: [PATCH 52/81] =?UTF-8?q?refactor:=20=EB=A9=94=EC=84=9C=EB=93=9C?= =?UTF-8?q?=20=EB=B6=84=EB=A6=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/view/OutputView.java | 38 +++++++++++--------- 1 file changed, 21 insertions(+), 17 deletions(-) diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index 87d3e7a6fe1..688654d07bb 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -7,6 +7,7 @@ import blackjack.model.gameresult.GameResult; import blackjack.model.user.Player; import blackjack.model.gameresult.PlayersGameResult; +import blackjack.model.user.User; import blackjack.model.user.Users; import java.util.EnumMap; import java.util.List; @@ -22,7 +23,6 @@ public static void printInitCards(Users users) { .map(Player::getName) .toList(); StringBuilder sb = new StringBuilder(); - sb.append("\n"); sb.append("딜러와 "); sb.append(String.join(", ", names)); sb.append("에게 2장을 나누었습니다."); @@ -37,14 +37,11 @@ public static void printInitCards(Users users) { private static void printDealerCard(Dealer dealer) { Card firstCard = dealer.cards().getFirst(); - System.out.println("딜러카드: " + firstCard.getRank().getFormat() + firstCard.getSuit().getFormat()); + System.out.println("딜러카드: " + getCardFormat(firstCard)); } public static void printPlayerCards(Player player) { - String cardsFormat = player.cards().stream() - .map(card -> card.getRank().getFormat() + card.getSuit().getFormat()) - .collect(Collectors.joining(", ")); - + String cardsFormat = getCardsFormat(player); System.out.println(player.getName() + "카드: " + cardsFormat); } @@ -61,18 +58,9 @@ public static void printHandStatus(Users users) { List players = users.getPlayers(); StringBuilder sb = new StringBuilder(); - sb.append(dealer.getName()).append(" 카드: "); - sb.append(dealer.cards().stream() - .map(card -> card.getRank().getFormat() + card.getSuit().getFormat()) - .collect(Collectors.joining(", "))); - sb.append(" - 결과: ").append(dealer.totalScore()).append("\n"); - + createHandStatusFormat(sb, dealer); for (Player player : players) { - sb.append(player.getName()).append(" 카드: "); - sb.append(player.cards().stream() - .map(card -> card.getRank().getFormat() + card.getSuit().getFormat()) - .collect(Collectors.joining(", "))); - sb.append(" - 결과: ").append(player.totalScore()).append("\n"); + createHandStatusFormat(sb, player); } System.out.println(sb); } @@ -98,4 +86,20 @@ public static void printGameResult(PlayersGameResult playersGameResult, Users us public static void printError(String errorMessage) { System.out.println("[ERROR] " + errorMessage); } + + private static void createHandStatusFormat(StringBuilder sb, User user) { + sb.append(user.getName()).append(" 카드: "); + sb.append(getCardsFormat(user)); + sb.append(" - 결과: ").append(user.totalScore()).append("\n"); + } + + private static String getCardsFormat(User user) { + return user.cards().stream() + .map(OutputView::getCardFormat) + .collect(Collectors.joining(", ")); + } + + private static String getCardFormat(Card card) { + return card.getRank().getFormat() + card.getSuit().getFormat(); + } } From 4b56ae8337126d05f0567b62b5931a1b361cf745 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 13:33:43 +0900 Subject: [PATCH 53/81] =?UTF-8?q?refactor:=20ErrorMessage=20=ED=81=B4?= =?UTF-8?q?=EB=9E=98=EC=8A=A4=20=EC=A0=9C=EA=B1=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/card/HitCommand.java | 9 ++++----- src/main/java/blackjack/model/constant/ErrorMessage.java | 6 +++--- src/main/java/blackjack/model/user/Username.java | 9 ++++----- .../blackjack/model/{ => card}/CardProviderTest.java | 0 src/test/java/blackjack/model/{ => card}/HandTest.java | 0 .../java/blackjack/model/{ => card}/HitCommandTest.java | 2 +- .../blackjack/{util => model/user}/PlayerParserTest.java | 0 7 files changed, 12 insertions(+), 14 deletions(-) rename src/test/java/blackjack/model/{ => card}/CardProviderTest.java (100%) rename src/test/java/blackjack/model/{ => card}/HandTest.java (100%) rename src/test/java/blackjack/model/{ => card}/HitCommandTest.java (95%) rename src/test/java/blackjack/{util => model/user}/PlayerParserTest.java (100%) diff --git a/src/main/java/blackjack/model/card/HitCommand.java b/src/main/java/blackjack/model/card/HitCommand.java index 66ba59fff6d..bdc8721d26b 100644 --- a/src/main/java/blackjack/model/card/HitCommand.java +++ b/src/main/java/blackjack/model/card/HitCommand.java @@ -1,12 +1,11 @@ package blackjack.model.card; -import static blackjack.model.constant.ErrorMessage.ERROR_EMPTY_INPUT; -import static blackjack.model.constant.ErrorMessage.ERROR_NOT_Y_N_INPUT; - import java.util.regex.Pattern; public class HitCommand { + private static final String ERROR_EMPTY_INPUT = "입력값은 공백일 수 없습니다."; + private static final String ERROR_NOT_Y_N_INPUT = "입력값은 y 또는 n만 가능합니다."; private static final String Y_N_REGEX = "^[yYnN]$"; private final String command; @@ -23,13 +22,13 @@ public boolean isY() { private void validateEmpty(String command) { if (command.isBlank()) { - throw new IllegalArgumentException(ERROR_EMPTY_INPUT.getErrorMessage()); + throw new IllegalArgumentException(ERROR_EMPTY_INPUT); } } private void validateRegex(String command) { if (!Pattern.matches(Y_N_REGEX, command)) { - throw new IllegalArgumentException(ERROR_NOT_Y_N_INPUT.getErrorMessage()); + throw new IllegalArgumentException(ERROR_NOT_Y_N_INPUT); } } } diff --git a/src/main/java/blackjack/model/constant/ErrorMessage.java b/src/main/java/blackjack/model/constant/ErrorMessage.java index 7aa3f071b21..b8ffbde8721 100644 --- a/src/main/java/blackjack/model/constant/ErrorMessage.java +++ b/src/main/java/blackjack/model/constant/ErrorMessage.java @@ -2,9 +2,9 @@ public enum ErrorMessage { - ERROR_EMPTY_INPUT("입력값은 공백일 수 없습니다."), - ERROR_NOT_Y_N_INPUT("입력값은 y 또는 n만 가능합니다."), - ERROR_INVALID_PLAYER_NAME("플레이어의 이름은 영어 or 한글로만 이루어질 수 있습니다."), +// ERROR_EMPTY_INPUT("입력값은 공백일 수 없습니다."), +// ERROR_NOT_Y_N_INPUT("입력값은 y 또는 n만 가능합니다."), +// ERROR_INVALID_PLAYER_NAME("플레이어의 이름은 영어 or 한글로만 이루어질 수 있습니다."), ; private final String errorMessage; diff --git a/src/main/java/blackjack/model/user/Username.java b/src/main/java/blackjack/model/user/Username.java index f429dfb5412..c94bc0f58e3 100644 --- a/src/main/java/blackjack/model/user/Username.java +++ b/src/main/java/blackjack/model/user/Username.java @@ -1,12 +1,11 @@ package blackjack.model.user; -import static blackjack.model.constant.ErrorMessage.ERROR_EMPTY_INPUT; -import static blackjack.model.constant.ErrorMessage.ERROR_INVALID_PLAYER_NAME; - import java.util.regex.Pattern; public class Username { + private static final String ERROR_EMPTY_INPUT = "입력값은 공백일 수 없습니다."; + private static final String ERROR_INVALID_PLAYER_NAME = "플레이어의 이름은 영어 or 한글로만 이루어질 수 있습니다."; private static final String PLAYER_NAME_REGEX = "^[a-zA-Z가-힣]*$"; private final String name; @@ -23,13 +22,13 @@ public String getName() { private void validateEmpty(String name) { if (name.isBlank()) { - throw new IllegalArgumentException(ERROR_EMPTY_INPUT.getErrorMessage()); + throw new IllegalArgumentException(ERROR_EMPTY_INPUT); } } private void validateRegex(String name) { if (!Pattern.matches(PLAYER_NAME_REGEX, name)) { - throw new IllegalArgumentException(ERROR_INVALID_PLAYER_NAME.getErrorMessage()); + throw new IllegalArgumentException(ERROR_INVALID_PLAYER_NAME); } } } diff --git a/src/test/java/blackjack/model/CardProviderTest.java b/src/test/java/blackjack/model/card/CardProviderTest.java similarity index 100% rename from src/test/java/blackjack/model/CardProviderTest.java rename to src/test/java/blackjack/model/card/CardProviderTest.java diff --git a/src/test/java/blackjack/model/HandTest.java b/src/test/java/blackjack/model/card/HandTest.java similarity index 100% rename from src/test/java/blackjack/model/HandTest.java rename to src/test/java/blackjack/model/card/HandTest.java diff --git a/src/test/java/blackjack/model/HitCommandTest.java b/src/test/java/blackjack/model/card/HitCommandTest.java similarity index 95% rename from src/test/java/blackjack/model/HitCommandTest.java rename to src/test/java/blackjack/model/card/HitCommandTest.java index 930073a4ddd..69b17a60c2d 100644 --- a/src/test/java/blackjack/model/HitCommandTest.java +++ b/src/test/java/blackjack/model/card/HitCommandTest.java @@ -38,6 +38,6 @@ void create_hitCommand_fail_when_invalid_input(String invalidInput) { //when & then assertThatThrownBy(() -> new HitCommand(invalidInput)) .isInstanceOf(IllegalArgumentException.class) - .hasMessage(ERROR_NOT_Y_N_INPUT.getErrorMessage()); + .hasMessage(HitCommand.ERROR_NOT_Y_N_INPUT); } } \ No newline at end of file diff --git a/src/test/java/blackjack/util/PlayerParserTest.java b/src/test/java/blackjack/model/user/PlayerParserTest.java similarity index 100% rename from src/test/java/blackjack/util/PlayerParserTest.java rename to src/test/java/blackjack/model/user/PlayerParserTest.java From 0e7417d2ea4af728bc4dc416e564561774d587cc Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 13:34:11 +0900 Subject: [PATCH 54/81] =?UTF-8?q?test:=20=ED=8F=B4=EB=8D=94=20=EA=B5=AC?= =?UTF-8?q?=EC=A1=B0=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/test/java/blackjack/model/card/CardProviderTest.java | 3 +-- src/test/java/blackjack/model/card/HandTest.java | 6 +----- src/test/java/blackjack/model/card/HitCommandTest.java | 9 +++------ src/test/java/blackjack/model/user/PlayerParserTest.java | 4 +--- src/test/java/blackjack/model/user/UsernameTest.java | 8 ++------ 5 files changed, 8 insertions(+), 22 deletions(-) diff --git a/src/test/java/blackjack/model/card/CardProviderTest.java b/src/test/java/blackjack/model/card/CardProviderTest.java index 6f086bf4530..4295ef990e6 100644 --- a/src/test/java/blackjack/model/card/CardProviderTest.java +++ b/src/test/java/blackjack/model/card/CardProviderTest.java @@ -1,8 +1,7 @@ -package blackjack.model; +package blackjack.model.card; import static org.assertj.core.api.Assertions.assertThat; -import blackjack.model.card.CardProvider; import blackjack.model.user.Dealer; import blackjack.model.user.Player; import blackjack.model.user.Users; diff --git a/src/test/java/blackjack/model/card/HandTest.java b/src/test/java/blackjack/model/card/HandTest.java index 0fa5ef4c795..a84cf065793 100644 --- a/src/test/java/blackjack/model/card/HandTest.java +++ b/src/test/java/blackjack/model/card/HandTest.java @@ -1,11 +1,7 @@ -package blackjack.model; +package blackjack.model.card; import static org.assertj.core.api.Assertions.assertThat; -import blackjack.model.card.Card; -import blackjack.model.card.Hand; -import blackjack.model.card.Rank; -import blackjack.model.card.Suit; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; diff --git a/src/test/java/blackjack/model/card/HitCommandTest.java b/src/test/java/blackjack/model/card/HitCommandTest.java index 69b17a60c2d..6d0f6fac5f3 100644 --- a/src/test/java/blackjack/model/card/HitCommandTest.java +++ b/src/test/java/blackjack/model/card/HitCommandTest.java @@ -1,11 +1,10 @@ -package blackjack.model; +package blackjack.model.card; import static blackjack.model.constant.ErrorMessage.ERROR_EMPTY_INPUT; import static blackjack.model.constant.ErrorMessage.ERROR_NOT_Y_N_INPUT; import static org.assertj.core.api.Assertions.assertThatThrownBy; import static org.junit.jupiter.api.Assertions.assertDoesNotThrow; -import blackjack.model.card.HitCommand; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.ValueSource; @@ -27,8 +26,7 @@ void create_hitCommand_success(String hitCommand) { void create_hitCommand_fail_when_empty_input(String emptyInput) { //when & then assertThatThrownBy(() -> new HitCommand(emptyInput)) - .isInstanceOf(IllegalArgumentException.class) - .hasMessage(ERROR_EMPTY_INPUT.getErrorMessage()); + .isInstanceOf(IllegalArgumentException.class); } @ParameterizedTest @@ -37,7 +35,6 @@ void create_hitCommand_fail_when_empty_input(String emptyInput) { void create_hitCommand_fail_when_invalid_input(String invalidInput) { //when & then assertThatThrownBy(() -> new HitCommand(invalidInput)) - .isInstanceOf(IllegalArgumentException.class) - .hasMessage(HitCommand.ERROR_NOT_Y_N_INPUT); + .isInstanceOf(IllegalArgumentException.class); } } \ No newline at end of file diff --git a/src/test/java/blackjack/model/user/PlayerParserTest.java b/src/test/java/blackjack/model/user/PlayerParserTest.java index 61d1977162e..063320841b9 100644 --- a/src/test/java/blackjack/model/user/PlayerParserTest.java +++ b/src/test/java/blackjack/model/user/PlayerParserTest.java @@ -1,9 +1,7 @@ -package blackjack.util; +package blackjack.model.user; import static org.assertj.core.api.Assertions.assertThat; -import blackjack.model.user.Player; -import blackjack.model.user.PlayerParser; import java.util.List; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; diff --git a/src/test/java/blackjack/model/user/UsernameTest.java b/src/test/java/blackjack/model/user/UsernameTest.java index 0473f81c347..66c71715766 100644 --- a/src/test/java/blackjack/model/user/UsernameTest.java +++ b/src/test/java/blackjack/model/user/UsernameTest.java @@ -1,7 +1,5 @@ package blackjack.model.user; -import static blackjack.model.constant.ErrorMessage.ERROR_EMPTY_INPUT; -import static blackjack.model.constant.ErrorMessage.ERROR_INVALID_PLAYER_NAME; import static org.assertj.core.api.Assertions.assertThatThrownBy; import static org.junit.jupiter.api.Assertions.assertDoesNotThrow; @@ -25,8 +23,7 @@ void create_username_success(String username) { void create_username_fail_when_empty_name(String emptyName) { //when & then assertThatThrownBy(() -> new Username(emptyName)) - .isInstanceOf(IllegalArgumentException.class) - .hasMessage(ERROR_EMPTY_INPUT.getErrorMessage()); + .isInstanceOf(IllegalArgumentException.class); } @ParameterizedTest @@ -35,7 +32,6 @@ void create_username_fail_when_empty_name(String emptyName) { void create_username_fail_when_invalid_name(String invalidName) { //when & then assertThatThrownBy(() -> new Username(invalidName)) - .isInstanceOf(IllegalArgumentException.class) - .hasMessage(ERROR_INVALID_PLAYER_NAME.getErrorMessage()); + .isInstanceOf(IllegalArgumentException.class); } } \ No newline at end of file From 9c6c4047282796c0ca20d27825071aedecbd9f40 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 13:34:43 +0900 Subject: [PATCH 55/81] =?UTF-8?q?refactor:=20ErrorMessage=20=ED=81=B4?= =?UTF-8?q?=EB=9E=98=EC=8A=A4=20=EC=A0=9C=EA=B1=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../model/constant/ErrorMessage.java | 19 ------------------- 1 file changed, 19 deletions(-) delete mode 100644 src/main/java/blackjack/model/constant/ErrorMessage.java diff --git a/src/main/java/blackjack/model/constant/ErrorMessage.java b/src/main/java/blackjack/model/constant/ErrorMessage.java deleted file mode 100644 index b8ffbde8721..00000000000 --- a/src/main/java/blackjack/model/constant/ErrorMessage.java +++ /dev/null @@ -1,19 +0,0 @@ -package blackjack.model.constant; - -public enum ErrorMessage { - -// ERROR_EMPTY_INPUT("입력값은 공백일 수 없습니다."), -// ERROR_NOT_Y_N_INPUT("입력값은 y 또는 n만 가능합니다."), -// ERROR_INVALID_PLAYER_NAME("플레이어의 이름은 영어 or 한글로만 이루어질 수 있습니다."), - ; - - private final String errorMessage; - - ErrorMessage(String errorMessage) { - this.errorMessage = errorMessage; - } - - public String getErrorMessage() { - return errorMessage; - } -} From ebf96c600792070a8a399c3c1915c2a879dd2c4e Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 13:39:00 +0900 Subject: [PATCH 56/81] =?UTF-8?q?refactor:=20=EC=83=81=EC=88=98=20?= =?UTF-8?q?=ED=81=B4=EB=9E=98=EC=8A=A4=20=EC=A0=9C=EA=B1=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../java/blackjack/model/card/CardProvider.java | 6 +++--- src/main/java/blackjack/model/card/Hand.java | 12 ++++++------ .../java/blackjack/model/constant/Constant.java | 14 -------------- src/main/java/blackjack/model/user/Dealer.java | 6 ++++-- src/main/java/blackjack/model/user/Player.java | 6 +++--- src/main/java/blackjack/view/OutputView.java | 5 +++-- 6 files changed, 19 insertions(+), 30 deletions(-) delete mode 100644 src/main/java/blackjack/model/constant/Constant.java diff --git a/src/main/java/blackjack/model/card/CardProvider.java b/src/main/java/blackjack/model/card/CardProvider.java index 78ecc6bbd14..cfe0225d345 100644 --- a/src/main/java/blackjack/model/card/CardProvider.java +++ b/src/main/java/blackjack/model/card/CardProvider.java @@ -1,8 +1,5 @@ package blackjack.model.card; -import static blackjack.model.constant.Constant.INIT_CARDS_END_IDX; -import static blackjack.model.constant.Constant.INIT_CARDS_START_IDX; - import blackjack.model.user.Dealer; import blackjack.model.user.Player; import blackjack.model.user.User; @@ -15,6 +12,9 @@ public class CardProvider { + private static final int INIT_CARDS_START_IDX = 0; + private static final int INIT_CARDS_END_IDX = 2; + private final Queue deck = new LinkedList<>(); public CardProvider() { diff --git a/src/main/java/blackjack/model/card/Hand.java b/src/main/java/blackjack/model/card/Hand.java index e5df390ce82..a17d84d9604 100644 --- a/src/main/java/blackjack/model/card/Hand.java +++ b/src/main/java/blackjack/model/card/Hand.java @@ -1,11 +1,5 @@ package blackjack.model.card; -import static blackjack.model.constant.Constant.ACE_SCORE_ELEVEN; -import static blackjack.model.constant.Constant.ACE_SCORE_ONE; -import static blackjack.model.constant.Constant.INIT_CARDS_END_IDX; -import static blackjack.model.constant.Constant.INIT_CARDS_START_IDX; -import static blackjack.model.constant.Constant.BLACKJACK_SCORE; - import java.util.ArrayList; import java.util.List; import java.util.Map; @@ -13,6 +7,12 @@ public class Hand { + private static final int BLACKJACK_SCORE = 21; + private static final int INIT_CARDS_START_IDX = 0; + private static final int INIT_CARDS_END_IDX = 2; + private static final int ACE_SCORE_ONE = 1; + private static final int ACE_SCORE_ELEVEN = 11; + private final List cards; public Hand() { diff --git a/src/main/java/blackjack/model/constant/Constant.java b/src/main/java/blackjack/model/constant/Constant.java deleted file mode 100644 index f2389f6895d..00000000000 --- a/src/main/java/blackjack/model/constant/Constant.java +++ /dev/null @@ -1,14 +0,0 @@ -package blackjack.model.constant; - -public class Constant { - - public static final int DEALER_ADD_CARD_STAND = 17; - public static final int BLACKJACK_SCORE = 21; - - public static final int INIT_CARDS_START_IDX = 0; - public static final int INIT_CARDS_END_IDX = 2; - - public static final int ACE_SCORE_ONE = 1; - public static final int ACE_SCORE_ELEVEN = 11; - -} diff --git a/src/main/java/blackjack/model/user/Dealer.java b/src/main/java/blackjack/model/user/Dealer.java index af688a7ebe6..d0fce4b9184 100644 --- a/src/main/java/blackjack/model/user/Dealer.java +++ b/src/main/java/blackjack/model/user/Dealer.java @@ -1,10 +1,12 @@ package blackjack.model.user; -import blackjack.model.constant.Constant; import blackjack.model.gameresult.GameResult; import java.util.EnumMap; public class Dealer extends User { + + private static final int DEALER_ADD_CARD_STAND = 17; + private final EnumMap gameResults; public Dealer() { @@ -22,6 +24,6 @@ public void addResult(GameResult gameResult) { @Override public boolean isHitAvailable() { - return totalScore() < Constant.DEALER_ADD_CARD_STAND; + return totalScore() < DEALER_ADD_CARD_STAND; } } diff --git a/src/main/java/blackjack/model/user/Player.java b/src/main/java/blackjack/model/user/Player.java index 56c7825c638..8c3901d00ab 100644 --- a/src/main/java/blackjack/model/user/Player.java +++ b/src/main/java/blackjack/model/user/Player.java @@ -1,15 +1,15 @@ package blackjack.model.user; +public class Player extends User { -import blackjack.model.constant.Constant; + private static final int BLACKJACK_SCORE = 21; -public class Player extends User { public Player(String name) { super(name); } @Override public boolean isHitAvailable() { - return totalScore() < Constant.BLACKJACK_SCORE; + return totalScore() < BLACKJACK_SCORE; } } diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index 688654d07bb..99b6c48aeb3 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -1,7 +1,5 @@ package blackjack.view; -import static blackjack.model.constant.Constant.BLACKJACK_SCORE; - import blackjack.model.card.Card; import blackjack.model.user.Dealer; import blackjack.model.gameresult.GameResult; @@ -15,6 +13,9 @@ import java.util.stream.Collectors; public class OutputView { + + private static final int BLACKJACK_SCORE = 21; + public static void printInitCards(Users users) { List players = users.getPlayers(); Dealer dealer = users.getDealer(); From 9c2cab0222cf48bfc4d2d32cdf6e663194252e86 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 13:51:33 +0900 Subject: [PATCH 57/81] =?UTF-8?q?docs:=20=EB=B0=B0=ED=8C=85=20=EA=B8=B0?= =?UTF-8?q?=EB=8A=A5=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 28 ++++++++++++++++++---------- 1 file changed, 18 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index cc23089b189..40ad29d2b2c 100644 --- a/README.md +++ b/README.md @@ -10,20 +10,28 @@ [예외처리] 쉼표 외의 다른 문자를 구분자로 한 경우 IllegalArgumentException 예외를 발생시킨다. [예외처리] 입력값이 공백일 경우 IllegalArgumentException 예외를 발생시킨다. + +**2. [입력] 게임에 참여한 사람의 배팅 금액을 입력 받는다.** + + [예외처리] 입력값이 숫자가 아닐 경우 IllegalArgumentException 예외를 발생시킨다. + + [예외처리] 입력값이 공백일 경우 IllegalArgumentException 예외를 발생시킨다. -**2. [중간 과정] 딜러와 사용자에게 카드를 2장씩 나누어준다.** + [예외처리] 입력값이 0 이하일 경우 IllegalArgumentException 예외를 발생시킨다. + +**3. [중간 과정] 딜러와 사용자에게 카드를 2장씩 나누어준다.** [카드 조건] 덱은 1개만 사용한다.(A ~ K : 13 * 4 = 52장) -**3. [중간 과정] 딜러와 사용자의 최초 카드 합계를 구하며, 블랙잭 여부를 판단한다.** +**4. [중간 과정] 딜러와 사용자의 최초 카드 합계를 구하며, 블랙잭 여부를 판단한다.** [ACE 조건] ACE가 11이어도 21이 넘지 않는 경우에는 11, 넘는 경우에는 1로 계산한다. -**4. [출력] 카드 현황을 출력한다.** +**5. [출력] 카드 현황을 출력한다.** [출력 조건] 딜러는 첫 번째 카드만 출력한다. -**5. [입력] 사용자별로 카드 추가 지급 여부를 입력 받는다.** +**6. [입력] 사용자별로 카드 추가 지급 여부를 입력 받는다.** [예외처리] y, n 외의 다른 문자일 경우 IllegalArgumentException 예외를 발생시킨다. @@ -31,12 +39,12 @@ [지급 조건] 사용자가 y를 입력하고, 사용자의 현재 카드 합계가 21미만일 경우에 카드를 지급한다. -**6. [출력] 사용자별로 지급 현황을 출력한다.** +**7. [출력] 사용자별로 지급 현황을 출력한다.** -**7. [출력] 딜러의 카드 합계가 17 이상이 일 될 때까지 추가 지급 현황을 출력한다.** +**8. [출력] 딜러의 카드 합계가 17 이상이 일 될 때까지 추가 지급 현황을 출력한다.** -**8. [출력] 사용자별 카드 현황 및 결과를 출력한다.** +**9. [출력] 사용자별 카드 현황 및 결과를 출력한다.** -**9. [중간 과정] 최종 승패 여부를 계산한다.** - -**10. [출력] 최종 승패를 출력한다.** +**10. [중간 과정] 최종 승패 및 수익을 계산한다.** + +**11. [출력] 참여자별 최종 수익을 출력한다.** From 7a3a4cd6931143d627d15bb1bc1ecb728b79eb22 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 14:04:17 +0900 Subject: [PATCH 58/81] =?UTF-8?q?docs:=20=EA=B8=B0=EB=8A=A5=20=EC=88=98?= =?UTF-8?q?=EC=A0=95"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 40ad29d2b2c..48c69842369 100644 --- a/README.md +++ b/README.md @@ -12,11 +12,11 @@ [예외처리] 입력값이 공백일 경우 IllegalArgumentException 예외를 발생시킨다. **2. [입력] 게임에 참여한 사람의 배팅 금액을 입력 받는다.** + + [예외처리] 입력값이 공백일 경우 IllegalArgumentException 예외를 발생시킨다. [예외처리] 입력값이 숫자가 아닐 경우 IllegalArgumentException 예외를 발생시킨다. - [예외처리] 입력값이 공백일 경우 IllegalArgumentException 예외를 발생시킨다. - [예외처리] 입력값이 0 이하일 경우 IllegalArgumentException 예외를 발생시킨다. **3. [중간 과정] 딜러와 사용자에게 카드를 2장씩 나누어준다.** From f7121931b5ab50762d987e2f78e31d012099c1b3 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 14:56:44 +0900 Subject: [PATCH 59/81] =?UTF-8?q?refactor:=20Users=20=ED=95=84=EB=93=9C=20?= =?UTF-8?q?List=EB=A1=9C=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/user/Users.java | 31 ++++++++++++------- 1 file changed, 20 insertions(+), 11 deletions(-) diff --git a/src/main/java/blackjack/model/user/Users.java b/src/main/java/blackjack/model/user/Users.java index 4a00889229e..310d3913c1b 100644 --- a/src/main/java/blackjack/model/user/Users.java +++ b/src/main/java/blackjack/model/user/Users.java @@ -9,35 +9,44 @@ public class Users { - private final List players; - private final Dealer dealer; + private static final String ERROR_DEALER_NOT_FOUND = "딜러가 존재하지 않습니다."; + + private final List users; public Users(List players, Dealer dealer) { - this.players = players; - this.dealer = dealer; + users = new ArrayList<>(players); + users.add(dealer); } public Users(String playerNames) { - this.players = PlayerParser.parse(playerNames); - this.dealer = new Dealer(); + users = new ArrayList<>(PlayerParser.parse(playerNames)); + users.add(new Dealer()); } public List getPlayers() { - return List.copyOf(players); + return users.stream() + .filter(Player.class::isInstance) + .map(Player.class::cast) + .toList(); } public Dealer getDealer() { - return dealer; + return users.stream() + .filter(Dealer.class::isInstance) + .map(Dealer.class::cast) + .findFirst() + .orElseThrow(() -> new IllegalArgumentException(ERROR_DEALER_NOT_FOUND)); } public List getUsers() { - List users = new ArrayList<>(List.copyOf(players)); - users.add(dealer); - return users; + return List.copyOf(users); } public PlayersGameResult determineWinner() { Map result = new HashMap<>(); + List players = getPlayers(); + Dealer dealer = getDealer(); + for (Player player : players) { if (calculateWhenBlackjack(player, dealer, result)) { continue; From 5f0d2e337ca0705d7b19968e95e591132d107d73 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 15:02:02 +0900 Subject: [PATCH 60/81] =?UTF-8?q?refactor:=20BlackjackGame=20=EA=B0=9D?= =?UTF-8?q?=EC=B2=B4=20=EC=83=9D=EC=84=B1=20&=20Controller=20=EC=B1=85?= =?UTF-8?q?=EC=9E=84=20=EB=B6=84=EB=A6=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/Application.java | 2 +- src/main/java/blackjack/BlackjackGame.java | 12 ++++++++++++ .../blackjack/controller/BlackjackController.java | 7 +++++-- 3 files changed, 18 insertions(+), 3 deletions(-) create mode 100644 src/main/java/blackjack/BlackjackGame.java diff --git a/src/main/java/blackjack/Application.java b/src/main/java/blackjack/Application.java index 0d4617c5165..fc42af371c1 100644 --- a/src/main/java/blackjack/Application.java +++ b/src/main/java/blackjack/Application.java @@ -6,7 +6,7 @@ public class Application { public static void main(String[] args) { - BlackjackController blackjackController = new BlackjackController(new CardProvider()); + BlackjackController blackjackController = new BlackjackController(new CardProvider(), new BlackjackGame()); blackjackController.run(); } } diff --git a/src/main/java/blackjack/BlackjackGame.java b/src/main/java/blackjack/BlackjackGame.java new file mode 100644 index 00000000000..bb2743a5048 --- /dev/null +++ b/src/main/java/blackjack/BlackjackGame.java @@ -0,0 +1,12 @@ +package blackjack; + +import blackjack.model.user.Users; +import java.util.function.Supplier; + +public class BlackjackGame { + + public Users createUsers(Supplier readUsername) { + String input = readUsername.get(); + return new Users(input); + } +} diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index 03cde5fe19d..db0e7176031 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -2,6 +2,7 @@ import static blackjack.util.ExceptionHandler.retryUntilSuccess; +import blackjack.BlackjackGame; import blackjack.model.card.HitCommand; import blackjack.model.card.CardProvider; import blackjack.model.user.Dealer; @@ -16,13 +17,15 @@ public class BlackjackController { private final CardProvider cardProvider; + private final BlackjackGame blackjackGame; - public BlackjackController(CardProvider cardProvider) { + public BlackjackController(CardProvider cardProvider, BlackjackGame blackjackGame) { this.cardProvider = cardProvider; + this.blackjackGame = blackjackGame; } public void run() { - Users users = retryUntilSuccess(this::createUsers); + Users users = retryUntilSuccess(() -> blackjackGame.createUsers(InputView::readPlayerName)); provideInitCardsAndPrint(users); From d55053104de1fc6876852263984fb58823e8c7b6 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 15:18:30 +0900 Subject: [PATCH 61/81] =?UTF-8?q?feat:=20=EB=B0=B0=ED=8C=85=20=EA=B8=88?= =?UTF-8?q?=EC=95=A1=20=EC=9E=85=EB=A0=A5=20=EA=B8=B0=EB=8A=A5=20=EA=B5=AC?= =?UTF-8?q?=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/BlackjackGame.java | 16 +++++ .../controller/BlackjackController.java | 4 ++ src/main/java/blackjack/model/BetAmount.java | 42 +++++++++++++ src/main/java/blackjack/view/InputView.java | 5 ++ .../java/blackjack/model/BetAmountTest.java | 59 +++++++++++++++++++ 5 files changed, 126 insertions(+) create mode 100644 src/main/java/blackjack/model/BetAmount.java create mode 100644 src/test/java/blackjack/model/BetAmountTest.java diff --git a/src/main/java/blackjack/BlackjackGame.java b/src/main/java/blackjack/BlackjackGame.java index bb2743a5048..37e6e2fb754 100644 --- a/src/main/java/blackjack/BlackjackGame.java +++ b/src/main/java/blackjack/BlackjackGame.java @@ -1,6 +1,11 @@ package blackjack; +import blackjack.model.BetAmount; +import blackjack.model.user.Player; import blackjack.model.user.Users; +import java.util.ArrayList; +import java.util.List; +import java.util.function.Function; import java.util.function.Supplier; public class BlackjackGame { @@ -9,4 +14,15 @@ public Users createUsers(Supplier readUsername) { String input = readUsername.get(); return new Users(input); } + + public List createBetAmount(Function readBetAmount, Users users) { + List players = users.getPlayers(); + List betAmounts = new ArrayList<>(); + for (Player player : players) { + String input = readBetAmount.apply(player); + BetAmount betAmount = new BetAmount(player, input); + betAmounts.add(betAmount); + } + return betAmounts; + } } diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index db0e7176031..f7a1cf5f7e8 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -3,6 +3,7 @@ import static blackjack.util.ExceptionHandler.retryUntilSuccess; import blackjack.BlackjackGame; +import blackjack.model.BetAmount; import blackjack.model.card.HitCommand; import blackjack.model.card.CardProvider; import blackjack.model.user.Dealer; @@ -27,6 +28,9 @@ public BlackjackController(CardProvider cardProvider, BlackjackGame blackjackGam public void run() { Users users = retryUntilSuccess(() -> blackjackGame.createUsers(InputView::readPlayerName)); + List betAmounts = retryUntilSuccess( + () -> blackjackGame.createBetAmount(InputView::readBetAmount, users)); + provideInitCardsAndPrint(users); hit(users); diff --git a/src/main/java/blackjack/model/BetAmount.java b/src/main/java/blackjack/model/BetAmount.java new file mode 100644 index 00000000000..3973a6db462 --- /dev/null +++ b/src/main/java/blackjack/model/BetAmount.java @@ -0,0 +1,42 @@ +package blackjack.model; + +import blackjack.model.user.Player; + +public class BetAmount { + + private static final String ERROR_EMPTY_INPUT = "입력값은 공백일 수 없습니다."; + private static final String ERROR_BET_AMOUNT_NOT_INTEGER = "배팅 금액은 숫자 형태로 입력해야 합니다."; + private static final String ERROR_BET_AMOUNT_NOT_POSITIVE = "배팅 금액은 0 이상이어야 합니다."; + + private final Player player; + private final int amount; + + public BetAmount(Player player, String input) { + validateEmpty(input); + int amount = convertToInt(input); + validatePositive(amount); + + this.player = player; + this.amount = amount; + } + + private void validateEmpty(String input) { + if (input.isBlank()) { + throw new IllegalArgumentException(ERROR_EMPTY_INPUT); + } + } + + private void validatePositive(int amount) { + if (amount <= 0) { + throw new IllegalArgumentException(ERROR_BET_AMOUNT_NOT_POSITIVE); + } + } + + private int convertToInt(String input) { + try { + return Integer.parseInt(input); + } catch (NumberFormatException e) { + throw new IllegalArgumentException(ERROR_BET_AMOUNT_NOT_INTEGER); + } + } +} diff --git a/src/main/java/blackjack/view/InputView.java b/src/main/java/blackjack/view/InputView.java index 577bdde668b..44d08b622a8 100644 --- a/src/main/java/blackjack/view/InputView.java +++ b/src/main/java/blackjack/view/InputView.java @@ -11,6 +11,11 @@ public static String readPlayerName() { return sc.nextLine(); } + public static String readBetAmount(Player player) { + System.out.println(player.getName() + "의 배팅 금액은?"); + return sc.nextLine(); + } + public static String readCardAdd(Player player) { System.out.println(player.getName() + "는 한장의 카드를 더 받겠습니까?(예는 y, 아니오는 n)"); return sc.nextLine(); diff --git a/src/test/java/blackjack/model/BetAmountTest.java b/src/test/java/blackjack/model/BetAmountTest.java new file mode 100644 index 00000000000..7618ce1195d --- /dev/null +++ b/src/test/java/blackjack/model/BetAmountTest.java @@ -0,0 +1,59 @@ +package blackjack.model; + +import static org.junit.jupiter.api.Assertions.*; + +import blackjack.model.user.Player; +import org.assertj.core.api.Assertions; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.ValueSource; + +class BetAmountTest { + + @ParameterizedTest + @ValueSource(strings = {"1", "10"}) + @DisplayName("배팅 금액 정상 생성") + void createBetAmount_success(String input) { + // given + Player player = new Player("name"); + + //when & then + assertDoesNotThrow(() -> new BetAmount(player, input)); + } + + @ParameterizedTest + @ValueSource(strings = {"", " "}) + @DisplayName("입력값이 공백일 경우 예외 발생") + void createBetAmount_fail_when_input_is_empty(String emptyInput) { + // given + Player player = new Player("name"); + + //when & then + Assertions.assertThatThrownBy(() -> new BetAmount(player, emptyInput)) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @ValueSource(strings = {"a", "1a", "123*"}) + @DisplayName("입력값이 숫자 형태가 아닐 경우 예외 발생") + void createBetAmount_fail_when_input_is_not_number(String stringInput) { + // given + Player player = new Player("name"); + + //when & then + Assertions.assertThatThrownBy(() -> new BetAmount(player, stringInput)) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @ValueSource(strings = {"0", "-1"}) + @DisplayName("입력값이 양수가 아닐 경우 예외 발생") + void createBetAmount_fail_when_input_is_not_positive(String negativeInput) { + // given + Player player = new Player("name"); + + //when & then + Assertions.assertThatThrownBy(() -> new BetAmount(player, negativeInput)) + .isInstanceOf(IllegalArgumentException.class); + } +} \ No newline at end of file From 9047d7aa5b825d8a50a41ed3810c62a582d1ab98 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 15:19:00 +0900 Subject: [PATCH 62/81] =?UTF-8?q?chore:=20=EB=AF=B8=EC=82=AC=EC=9A=A9=20?= =?UTF-8?q?=EB=9D=BC=EC=9D=B4=EB=B8=8C=EB=9F=AC=EB=A6=AC=20=EC=A0=9C?= =?UTF-8?q?=EA=B1=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/test/java/blackjack/model/card/HitCommandTest.java | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/test/java/blackjack/model/card/HitCommandTest.java b/src/test/java/blackjack/model/card/HitCommandTest.java index 6d0f6fac5f3..98c40690317 100644 --- a/src/test/java/blackjack/model/card/HitCommandTest.java +++ b/src/test/java/blackjack/model/card/HitCommandTest.java @@ -1,7 +1,5 @@ package blackjack.model.card; -import static blackjack.model.constant.ErrorMessage.ERROR_EMPTY_INPUT; -import static blackjack.model.constant.ErrorMessage.ERROR_NOT_Y_N_INPUT; import static org.assertj.core.api.Assertions.assertThatThrownBy; import static org.junit.jupiter.api.Assertions.assertDoesNotThrow; From 1dffd25560867453d4bcc09ce7db1db027514877 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 15:45:59 +0900 Subject: [PATCH 63/81] =?UTF-8?q?refactor:=20Controller=20=EC=B1=85?= =?UTF-8?q?=EC=9E=84=20=EB=B6=84=EB=A6=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/Application.java | 2 +- src/main/java/blackjack/BlackjackGame.java | 48 +++++++++++++++++++ .../controller/BlackjackController.java | 47 ++---------------- src/main/java/blackjack/view/InputView.java | 2 +- 4 files changed, 54 insertions(+), 45 deletions(-) diff --git a/src/main/java/blackjack/Application.java b/src/main/java/blackjack/Application.java index fc42af371c1..93d2d360bb9 100644 --- a/src/main/java/blackjack/Application.java +++ b/src/main/java/blackjack/Application.java @@ -6,7 +6,7 @@ public class Application { public static void main(String[] args) { - BlackjackController blackjackController = new BlackjackController(new CardProvider(), new BlackjackGame()); + BlackjackController blackjackController = new BlackjackController(new BlackjackGame(new CardProvider())); blackjackController.run(); } } diff --git a/src/main/java/blackjack/BlackjackGame.java b/src/main/java/blackjack/BlackjackGame.java index 37e6e2fb754..7a9c708711d 100644 --- a/src/main/java/blackjack/BlackjackGame.java +++ b/src/main/java/blackjack/BlackjackGame.java @@ -1,8 +1,15 @@ package blackjack; +import static blackjack.util.ExceptionHandler.retryUntilSuccess; + import blackjack.model.BetAmount; +import blackjack.model.card.CardProvider; +import blackjack.model.card.HitCommand; +import blackjack.model.user.Dealer; import blackjack.model.user.Player; import blackjack.model.user.Users; +import blackjack.view.InputView; +import blackjack.view.OutputView; import java.util.ArrayList; import java.util.List; import java.util.function.Function; @@ -10,6 +17,12 @@ public class BlackjackGame { + private final CardProvider cardProvider; + + public BlackjackGame(CardProvider cardProvider) { + this.cardProvider = cardProvider; + } + public Users createUsers(Supplier readUsername) { String input = readUsername.get(); return new Users(input); @@ -25,4 +38,39 @@ public List createBetAmount(Function readBetAmount, U } return betAmounts; } + + public void provideInitCards(Users users) { + cardProvider.provideInitCards(users); + } + + public void hit(Users users, Function readHitCommand) { + List players = users.getPlayers(); + Dealer dealer = users.getDealer(); + + for (Player player : players) { + while (retryUntilSuccess(() -> checkY(player, readHitCommand)) && checkAddCard(player)) { + cardProvider.provideOneCard(player); + OutputView.printPlayerCards(player); + } + } + + while (dealer.isHitAvailable()) { + cardProvider.provideOneCard(dealer); + OutputView.printDealerHit(); + } + } + + private boolean checkY(Player player, Function readHitCommand) { + String input = readHitCommand.apply(player); + HitCommand hitCommand = new HitCommand(input); + return hitCommand.isY(); + } + + private boolean checkAddCard(Player player) { + if (player.isHitAvailable()) { + return true; + } + OutputView.printCantHit(); + return false; + } } diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index f7a1cf5f7e8..b516e17151d 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -5,10 +5,9 @@ import blackjack.BlackjackGame; import blackjack.model.BetAmount; import blackjack.model.card.HitCommand; -import blackjack.model.card.CardProvider; +import blackjack.model.gameresult.PlayersGameResult; import blackjack.model.user.Dealer; import blackjack.model.user.Player; -import blackjack.model.gameresult.PlayersGameResult; import blackjack.model.user.Users; import blackjack.view.InputView; import blackjack.view.OutputView; @@ -17,11 +16,9 @@ public class BlackjackController { - private final CardProvider cardProvider; private final BlackjackGame blackjackGame; - public BlackjackController(CardProvider cardProvider, BlackjackGame blackjackGame) { - this.cardProvider = cardProvider; + public BlackjackController(BlackjackGame blackjackGame) { this.blackjackGame = blackjackGame; } @@ -33,7 +30,7 @@ public void run() { provideInitCardsAndPrint(users); - hit(users); + blackjackGame.hit(users, InputView::readHitCommand); printHandStatus(users); @@ -42,33 +39,11 @@ public void run() { InputView.closeScanner(); } - private Users createUsers() { - String input = InputView.readPlayerName(); - return new Users(input); - } - private void provideInitCardsAndPrint(Users users) { - cardProvider.provideInitCards(users); + blackjackGame.provideInitCards(users); OutputView.printInitCards(users); } - private void hit(Users users) { - List players = users.getPlayers(); - Dealer dealer = users.getDealer(); - - for (Player player : players) { - while (retryUntilSuccess(() -> checkY(player)) && checkAddCard(player)) { - cardProvider.provideOneCard(player); - OutputView.printPlayerCards(player); - } - } - - while (dealer.isHitAvailable()) { - cardProvider.provideOneCard(dealer); - OutputView.printDealerHit(); - } - } - private void printHandStatus(Users users) { OutputView.printHandStatus(users); } @@ -77,18 +52,4 @@ private void printGameResult(Users users) { PlayersGameResult playersGameResult = users.determineWinner(); OutputView.printGameResult(playersGameResult, users); } - - private boolean checkY(Player player) { - String input = InputView.readCardAdd(player).trim(); - HitCommand hitCommand = new HitCommand(input); - return hitCommand.isY(); - } - - private boolean checkAddCard(Player player) { - if (player.isHitAvailable()) { - return true; - } - OutputView.printCantHit(); - return false; - } } diff --git a/src/main/java/blackjack/view/InputView.java b/src/main/java/blackjack/view/InputView.java index 44d08b622a8..0897f8dd3c0 100644 --- a/src/main/java/blackjack/view/InputView.java +++ b/src/main/java/blackjack/view/InputView.java @@ -16,7 +16,7 @@ public static String readBetAmount(Player player) { return sc.nextLine(); } - public static String readCardAdd(Player player) { + public static String readHitCommand(Player player) { System.out.println(player.getName() + "는 한장의 카드를 더 받겠습니까?(예는 y, 아니오는 n)"); return sc.nextLine(); } From a2712e26d5dae70ad82246b0bfbb6684444d4ae6 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 15:52:36 +0900 Subject: [PATCH 64/81] =?UTF-8?q?refactor:=20Controller=20=EC=B1=85?= =?UTF-8?q?=EC=9E=84=20=EB=B6=84=EB=A6=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/BlackjackGame.java | 5 +++++ src/main/java/blackjack/controller/BlackjackController.java | 5 +---- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/src/main/java/blackjack/BlackjackGame.java b/src/main/java/blackjack/BlackjackGame.java index 7a9c708711d..d260e90a6fa 100644 --- a/src/main/java/blackjack/BlackjackGame.java +++ b/src/main/java/blackjack/BlackjackGame.java @@ -5,6 +5,7 @@ import blackjack.model.BetAmount; import blackjack.model.card.CardProvider; import blackjack.model.card.HitCommand; +import blackjack.model.gameresult.PlayersGameResult; import blackjack.model.user.Dealer; import blackjack.model.user.Player; import blackjack.model.user.Users; @@ -60,6 +61,10 @@ public void hit(Users users, Function readHitCommand) { } } + public PlayersGameResult determineWinner(Users users) { + return users.determineWinner(); + } + private boolean checkY(Player player, Function readHitCommand) { String input = readHitCommand.apply(player); HitCommand hitCommand = new HitCommand(input); diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index b516e17151d..ae85cb5d01e 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -4,10 +4,7 @@ import blackjack.BlackjackGame; import blackjack.model.BetAmount; -import blackjack.model.card.HitCommand; import blackjack.model.gameresult.PlayersGameResult; -import blackjack.model.user.Dealer; -import blackjack.model.user.Player; import blackjack.model.user.Users; import blackjack.view.InputView; import blackjack.view.OutputView; @@ -49,7 +46,7 @@ private void printHandStatus(Users users) { } private void printGameResult(Users users) { - PlayersGameResult playersGameResult = users.determineWinner(); + PlayersGameResult playersGameResult = blackjackGame.determineWinner(users); OutputView.printGameResult(playersGameResult, users); } } From ffa2e7001c299a7a985cfa39bf3456271c0c5d23 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 16:30:05 +0900 Subject: [PATCH 65/81] =?UTF-8?q?refactor:=20BetAmounts=20=ED=95=84?= =?UTF-8?q?=EB=93=9C=20=EC=9E=90=EB=A3=8C=EA=B5=AC=EC=A1=B0=20=EC=88=98?= =?UTF-8?q?=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/BlackjackGame.java | 14 +++++++++----- src/main/java/blackjack/model/BetAmounts.java | 15 +++++++++++++++ 2 files changed, 24 insertions(+), 5 deletions(-) create mode 100644 src/main/java/blackjack/model/BetAmounts.java diff --git a/src/main/java/blackjack/BlackjackGame.java b/src/main/java/blackjack/BlackjackGame.java index d260e90a6fa..9392b2c5432 100644 --- a/src/main/java/blackjack/BlackjackGame.java +++ b/src/main/java/blackjack/BlackjackGame.java @@ -3,6 +3,7 @@ import static blackjack.util.ExceptionHandler.retryUntilSuccess; import blackjack.model.BetAmount; +import blackjack.model.BetAmounts; import blackjack.model.card.CardProvider; import blackjack.model.card.HitCommand; import blackjack.model.gameresult.PlayersGameResult; @@ -12,7 +13,9 @@ import blackjack.view.InputView; import blackjack.view.OutputView; import java.util.ArrayList; +import java.util.HashMap; import java.util.List; +import java.util.Map; import java.util.function.Function; import java.util.function.Supplier; @@ -29,15 +32,15 @@ public Users createUsers(Supplier readUsername) { return new Users(input); } - public List createBetAmount(Function readBetAmount, Users users) { + public BetAmounts createBetAmount(Function readBetAmount, Users users) { List players = users.getPlayers(); - List betAmounts = new ArrayList<>(); + Map betAmounts = new HashMap<>(); for (Player player : players) { String input = readBetAmount.apply(player); BetAmount betAmount = new BetAmount(player, input); - betAmounts.add(betAmount); + betAmounts.put(player, betAmount); } - return betAmounts; + return new BetAmounts(betAmounts); } public void provideInitCards(Users users) { @@ -61,7 +64,8 @@ public void hit(Users users, Function readHitCommand) { } } - public PlayersGameResult determineWinner(Users users) { + public PlayersGameResult determineWinner(Users users, BetAmounts betAmounts) { + return users.determineWinner(); } diff --git a/src/main/java/blackjack/model/BetAmounts.java b/src/main/java/blackjack/model/BetAmounts.java new file mode 100644 index 00000000000..d7ea1f6f950 --- /dev/null +++ b/src/main/java/blackjack/model/BetAmounts.java @@ -0,0 +1,15 @@ +package blackjack.model; + +import blackjack.model.user.Player; +import java.util.Map; + +public class BetAmounts { + + private final Map betAmounts; + + public BetAmounts(Map betAmounts) { + this.betAmounts = betAmounts; + } + + +} From 4b142e6135d28a97aeed4b785c891554641bb900 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 18:09:23 +0900 Subject: [PATCH 66/81] =?UTF-8?q?feat:=20=EC=88=98=EC=9D=B5=20=EA=B3=84?= =?UTF-8?q?=EC=82=B0=20=EB=B0=8F=20=EC=B6=9C=EB=A0=A5=20=EA=B8=B0=EB=8A=A5?= =?UTF-8?q?=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/BlackjackGame.java | 11 +- .../controller/BlackjackController.java | 15 ++- src/main/java/blackjack/model/BetAmount.java | 11 +- src/main/java/blackjack/model/BetAmounts.java | 17 +++ ...ayersGameResult.java => ProfitResult.java} | 2 +- src/main/java/blackjack/model/user/Users.java | 105 +++++++----------- src/main/java/blackjack/view/OutputView.java | 18 +-- .../java/blackjack/model/BetAmountTest.java | 8 +- 8 files changed, 85 insertions(+), 102 deletions(-) rename src/main/java/blackjack/model/gameresult/{PlayersGameResult.java => ProfitResult.java} (54%) diff --git a/src/main/java/blackjack/BlackjackGame.java b/src/main/java/blackjack/BlackjackGame.java index 9392b2c5432..91e246e747e 100644 --- a/src/main/java/blackjack/BlackjackGame.java +++ b/src/main/java/blackjack/BlackjackGame.java @@ -6,13 +6,11 @@ import blackjack.model.BetAmounts; import blackjack.model.card.CardProvider; import blackjack.model.card.HitCommand; -import blackjack.model.gameresult.PlayersGameResult; +import blackjack.model.gameresult.ProfitResult; import blackjack.model.user.Dealer; import blackjack.model.user.Player; import blackjack.model.user.Users; -import blackjack.view.InputView; import blackjack.view.OutputView; -import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; @@ -37,7 +35,7 @@ public BetAmounts createBetAmount(Function readBetAmount, Users Map betAmounts = new HashMap<>(); for (Player player : players) { String input = readBetAmount.apply(player); - BetAmount betAmount = new BetAmount(player, input); + BetAmount betAmount = new BetAmount(input); betAmounts.put(player, betAmount); } return new BetAmounts(betAmounts); @@ -64,9 +62,8 @@ public void hit(Users users, Function readHitCommand) { } } - public PlayersGameResult determineWinner(Users users, BetAmounts betAmounts) { - - return users.determineWinner(); + public ProfitResult determineWinner(Users users, BetAmounts betAmounts) { + return users.determineWinner(betAmounts); } private boolean checkY(Player player, Function readHitCommand) { diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index ae85cb5d01e..43447b40799 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -3,12 +3,11 @@ import static blackjack.util.ExceptionHandler.retryUntilSuccess; import blackjack.BlackjackGame; -import blackjack.model.BetAmount; -import blackjack.model.gameresult.PlayersGameResult; +import blackjack.model.BetAmounts; +import blackjack.model.gameresult.ProfitResult; import blackjack.model.user.Users; import blackjack.view.InputView; import blackjack.view.OutputView; -import java.util.List; public class BlackjackController { @@ -22,7 +21,7 @@ public BlackjackController(BlackjackGame blackjackGame) { public void run() { Users users = retryUntilSuccess(() -> blackjackGame.createUsers(InputView::readPlayerName)); - List betAmounts = retryUntilSuccess( + BetAmounts betAmounts = retryUntilSuccess( () -> blackjackGame.createBetAmount(InputView::readBetAmount, users)); provideInitCardsAndPrint(users); @@ -31,7 +30,7 @@ public void run() { printHandStatus(users); - printGameResult(users); + printProfitResult(users, betAmounts); InputView.closeScanner(); } @@ -45,8 +44,8 @@ private void printHandStatus(Users users) { OutputView.printHandStatus(users); } - private void printGameResult(Users users) { - PlayersGameResult playersGameResult = blackjackGame.determineWinner(users); - OutputView.printGameResult(playersGameResult, users); + private void printProfitResult(Users users, BetAmounts betAmounts) { + ProfitResult profitResult = blackjackGame.determineWinner(users, betAmounts); + OutputView.printGameResult(profitResult, users); } } diff --git a/src/main/java/blackjack/model/BetAmount.java b/src/main/java/blackjack/model/BetAmount.java index 3973a6db462..b3375b990a2 100644 --- a/src/main/java/blackjack/model/BetAmount.java +++ b/src/main/java/blackjack/model/BetAmount.java @@ -1,25 +1,24 @@ package blackjack.model; -import blackjack.model.user.Player; - public class BetAmount { private static final String ERROR_EMPTY_INPUT = "입력값은 공백일 수 없습니다."; private static final String ERROR_BET_AMOUNT_NOT_INTEGER = "배팅 금액은 숫자 형태로 입력해야 합니다."; private static final String ERROR_BET_AMOUNT_NOT_POSITIVE = "배팅 금액은 0 이상이어야 합니다."; - private final Player player; private final int amount; - public BetAmount(Player player, String input) { + public BetAmount(String input) { validateEmpty(input); int amount = convertToInt(input); validatePositive(amount); - - this.player = player; this.amount = amount; } + public int getAmount() { + return amount; + } + private void validateEmpty(String input) { if (input.isBlank()) { throw new IllegalArgumentException(ERROR_EMPTY_INPUT); diff --git a/src/main/java/blackjack/model/BetAmounts.java b/src/main/java/blackjack/model/BetAmounts.java index d7ea1f6f950..a7ae1e4df26 100644 --- a/src/main/java/blackjack/model/BetAmounts.java +++ b/src/main/java/blackjack/model/BetAmounts.java @@ -11,5 +11,22 @@ public BetAmounts(Map betAmounts) { this.betAmounts = betAmounts; } + public int calculateWinPayout(Player player) { + BetAmount betAmount = betAmounts.get(player); + return betAmount.getAmount(); + } + + public int calculateLosePayout(Player player) { + BetAmount betAmount = betAmounts.get(player); + return -betAmount.getAmount(); + } + public int calculateBlackjackPayout(Player player) { + BetAmount betAmount = betAmounts.get(player); + return (int) Math.round(betAmount.getAmount() * 1.5); + } + + public int calculateDrawPayout() { + return 0; + } } diff --git a/src/main/java/blackjack/model/gameresult/PlayersGameResult.java b/src/main/java/blackjack/model/gameresult/ProfitResult.java similarity index 54% rename from src/main/java/blackjack/model/gameresult/PlayersGameResult.java rename to src/main/java/blackjack/model/gameresult/ProfitResult.java index 6440361a6a7..df310ae6b7a 100644 --- a/src/main/java/blackjack/model/gameresult/PlayersGameResult.java +++ b/src/main/java/blackjack/model/gameresult/ProfitResult.java @@ -3,5 +3,5 @@ import blackjack.model.user.Player; import java.util.Map; -public record PlayersGameResult(Map result) { +public record ProfitResult(Map playersProfit, int dealerProfit) { } diff --git a/src/main/java/blackjack/model/user/Users.java b/src/main/java/blackjack/model/user/Users.java index 310d3913c1b..0b931bf0eb9 100644 --- a/src/main/java/blackjack/model/user/Users.java +++ b/src/main/java/blackjack/model/user/Users.java @@ -1,7 +1,7 @@ package blackjack.model.user; -import blackjack.model.gameresult.GameResult; -import blackjack.model.gameresult.PlayersGameResult; +import blackjack.model.BetAmounts; +import blackjack.model.gameresult.ProfitResult; import java.util.ArrayList; import java.util.HashMap; import java.util.List; @@ -42,84 +42,61 @@ public List getUsers() { return List.copyOf(users); } - public PlayersGameResult determineWinner() { - Map result = new HashMap<>(); + public ProfitResult determineWinner(BetAmounts betAmounts) { + Map result = new HashMap<>(); + int dealerPayout = 0; List players = getPlayers(); Dealer dealer = getDealer(); for (Player player : players) { - if (calculateWhenBlackjack(player, dealer, result)) { + if (player.isBust()) { + result.put(player, betAmounts.calculateLosePayout(player)); + dealerPayout += betAmounts.calculateWinPayout(player); continue; } - if (calculateWhenBust(player, dealer, result)) { + if (player.isBlackjack() && dealer.isBlackjack()) { + result.put(player, betAmounts.calculateDrawPayout()); + dealerPayout += betAmounts.calculateDrawPayout(); continue; } - calculateWhenNormal(player, dealer, result); - } - return new PlayersGameResult(result); - } - - private boolean calculateWhenBlackjack(Player player, Dealer dealer, Map result) { - if (player.isBlackjack() && dealer.isBlackjack()) { - logDraw(player, dealer, result); - return true; - } - - if (player.isBlackjack()) { - logPlayerWin(player, dealer, result); - return true; - } - - if (dealer.isBlackjack()) { - logPlayerLose(player, dealer, result); - return true; - } - - return false; - } + if (player.isBlackjack()) { + result.put(player, betAmounts.calculateBlackjackPayout(player)); + dealerPayout -= betAmounts.calculateBlackjackPayout(player); + continue; + } - private boolean calculateWhenBust(Player player, Dealer dealer, Map result) { - if (player.isBust()) { - logPlayerLose(player, dealer, result); - return true; - } + if (dealer.isBlackjack()) { + result.put(player, betAmounts.calculateLosePayout(player)); + dealerPayout += betAmounts.calculateWinPayout(player); + continue; + } - if (dealer.isBust()) { - logPlayerWin(player, dealer, result); - return true; - } + if (dealer.isBust()) { + result.put(player, betAmounts.calculateWinPayout(player)); + dealerPayout -= betAmounts.calculateWinPayout(player); + continue; + } - return false; - } + if (dealer.totalScore() == player.totalScore()) { + result.put(player, betAmounts.calculateDrawPayout()); + dealerPayout += betAmounts.calculateDrawPayout(); + continue; + } - private void calculateWhenNormal(Player player, Dealer dealer, Map result) { - if (player.totalScore() > dealer.totalScore()) { - logPlayerWin(player, dealer, result); - return; - } + if (dealer.totalScore() > player.totalScore()) { + result.put(player, betAmounts.calculateLosePayout(player)); + dealerPayout += betAmounts.calculateWinPayout(player); + continue; + } - if (player.totalScore() < dealer.totalScore()) { - logPlayerLose(player, dealer, result); - return; + if (dealer.totalScore() < player.totalScore()) { + result.put(player, betAmounts.calculateWinPayout(player)); + dealerPayout -= betAmounts.calculateWinPayout(player); + } } - logDraw(player, dealer, result); - } - - private void logPlayerWin(Player player, Dealer dealer, Map result) { - result.put(player, GameResult.WIN); - dealer.addResult(GameResult.LOSE); - } - - private void logPlayerLose(Player player, Dealer dealer, Map result) { - result.put(player, GameResult.LOSE); - dealer.addResult(GameResult.WIN); - } - - private void logDraw(Player player, Dealer dealer, Map result) { - result.put(player, GameResult.DRAW); - dealer.addResult(GameResult.DRAW); + return new ProfitResult(result, dealerPayout); } } diff --git a/src/main/java/blackjack/view/OutputView.java b/src/main/java/blackjack/view/OutputView.java index 99b6c48aeb3..cb53c6871fc 100644 --- a/src/main/java/blackjack/view/OutputView.java +++ b/src/main/java/blackjack/view/OutputView.java @@ -1,13 +1,11 @@ package blackjack.view; import blackjack.model.card.Card; +import blackjack.model.gameresult.ProfitResult; import blackjack.model.user.Dealer; -import blackjack.model.gameresult.GameResult; import blackjack.model.user.Player; -import blackjack.model.gameresult.PlayersGameResult; import blackjack.model.user.User; import blackjack.model.user.Users; -import java.util.EnumMap; import java.util.List; import java.util.Map; import java.util.stream.Collectors; @@ -66,21 +64,17 @@ public static void printHandStatus(Users users) { System.out.println(sb); } - public static void printGameResult(PlayersGameResult playersGameResult, Users users) { + public static void printGameResult(ProfitResult profitResult, Users users) { System.out.println(); - System.out.println("## 최종 승패"); + System.out.println("## 최종 수익"); Dealer dealer = users.getDealer(); - EnumMap dealerGameResult = dealer.getGameResults(); - System.out.println( - dealer.getName() + ": " + dealerGameResult.getOrDefault(GameResult.WIN, 0) + "승 " + - dealerGameResult.getOrDefault(GameResult.DRAW, 0) + "무 " + dealerGameResult.getOrDefault( - GameResult.LOSE, 0) + "패"); + System.out.println(dealer.getName() + ": " + profitResult.dealerProfit()); - Map result = playersGameResult.result(); + Map playersProfit = profitResult.playersProfit(); for (Player player : users.getPlayers()) { System.out.print(player.getName() + ": "); - System.out.println(result.get(player).getFormat()); + System.out.println(playersProfit.get(player)); } } diff --git a/src/test/java/blackjack/model/BetAmountTest.java b/src/test/java/blackjack/model/BetAmountTest.java index 7618ce1195d..50f864dd992 100644 --- a/src/test/java/blackjack/model/BetAmountTest.java +++ b/src/test/java/blackjack/model/BetAmountTest.java @@ -18,7 +18,7 @@ void createBetAmount_success(String input) { Player player = new Player("name"); //when & then - assertDoesNotThrow(() -> new BetAmount(player, input)); + assertDoesNotThrow(() -> new BetAmount(input)); } @ParameterizedTest @@ -29,7 +29,7 @@ void createBetAmount_fail_when_input_is_empty(String emptyInput) { Player player = new Player("name"); //when & then - Assertions.assertThatThrownBy(() -> new BetAmount(player, emptyInput)) + Assertions.assertThatThrownBy(() -> new BetAmount(emptyInput)) .isInstanceOf(IllegalArgumentException.class); } @@ -41,7 +41,7 @@ void createBetAmount_fail_when_input_is_not_number(String stringInput) { Player player = new Player("name"); //when & then - Assertions.assertThatThrownBy(() -> new BetAmount(player, stringInput)) + Assertions.assertThatThrownBy(() -> new BetAmount(stringInput)) .isInstanceOf(IllegalArgumentException.class); } @@ -53,7 +53,7 @@ void createBetAmount_fail_when_input_is_not_positive(String negativeInput) { Player player = new Player("name"); //when & then - Assertions.assertThatThrownBy(() -> new BetAmount(player, negativeInput)) + Assertions.assertThatThrownBy(() -> new BetAmount(negativeInput)) .isInstanceOf(IllegalArgumentException.class); } } \ No newline at end of file From ba922a4953d291bd5367b9227785e849cf44a9b5 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Thu, 12 Mar 2026 18:13:33 +0900 Subject: [PATCH 67/81] =?UTF-8?q?refactor:=20=ED=8F=B4=EB=8D=94=20?= =?UTF-8?q?=EA=B5=AC=EC=A1=B0=20=EB=B3=80=EA=B2=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/BlackjackGame.java | 4 ++-- src/main/java/blackjack/controller/BlackjackController.java | 2 +- src/main/java/blackjack/model/{ => bet}/BetAmount.java | 2 +- src/main/java/blackjack/model/{ => bet}/BetAmounts.java | 2 +- src/main/java/blackjack/model/user/Users.java | 2 +- src/test/java/blackjack/model/BetAmountTest.java | 1 + 6 files changed, 7 insertions(+), 6 deletions(-) rename src/main/java/blackjack/model/{ => bet}/BetAmount.java (97%) rename src/main/java/blackjack/model/{ => bet}/BetAmounts.java (96%) diff --git a/src/main/java/blackjack/BlackjackGame.java b/src/main/java/blackjack/BlackjackGame.java index 91e246e747e..369b0b58b59 100644 --- a/src/main/java/blackjack/BlackjackGame.java +++ b/src/main/java/blackjack/BlackjackGame.java @@ -2,8 +2,8 @@ import static blackjack.util.ExceptionHandler.retryUntilSuccess; -import blackjack.model.BetAmount; -import blackjack.model.BetAmounts; +import blackjack.model.bet.BetAmount; +import blackjack.model.bet.BetAmounts; import blackjack.model.card.CardProvider; import blackjack.model.card.HitCommand; import blackjack.model.gameresult.ProfitResult; diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index 43447b40799..39179586422 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -3,7 +3,7 @@ import static blackjack.util.ExceptionHandler.retryUntilSuccess; import blackjack.BlackjackGame; -import blackjack.model.BetAmounts; +import blackjack.model.bet.BetAmounts; import blackjack.model.gameresult.ProfitResult; import blackjack.model.user.Users; import blackjack.view.InputView; diff --git a/src/main/java/blackjack/model/BetAmount.java b/src/main/java/blackjack/model/bet/BetAmount.java similarity index 97% rename from src/main/java/blackjack/model/BetAmount.java rename to src/main/java/blackjack/model/bet/BetAmount.java index b3375b990a2..aa45d95d5e1 100644 --- a/src/main/java/blackjack/model/BetAmount.java +++ b/src/main/java/blackjack/model/bet/BetAmount.java @@ -1,4 +1,4 @@ -package blackjack.model; +package blackjack.model.bet; public class BetAmount { diff --git a/src/main/java/blackjack/model/BetAmounts.java b/src/main/java/blackjack/model/bet/BetAmounts.java similarity index 96% rename from src/main/java/blackjack/model/BetAmounts.java rename to src/main/java/blackjack/model/bet/BetAmounts.java index a7ae1e4df26..6f058ae02c1 100644 --- a/src/main/java/blackjack/model/BetAmounts.java +++ b/src/main/java/blackjack/model/bet/BetAmounts.java @@ -1,4 +1,4 @@ -package blackjack.model; +package blackjack.model.bet; import blackjack.model.user.Player; import java.util.Map; diff --git a/src/main/java/blackjack/model/user/Users.java b/src/main/java/blackjack/model/user/Users.java index 0b931bf0eb9..b45902b1a63 100644 --- a/src/main/java/blackjack/model/user/Users.java +++ b/src/main/java/blackjack/model/user/Users.java @@ -1,6 +1,6 @@ package blackjack.model.user; -import blackjack.model.BetAmounts; +import blackjack.model.bet.BetAmounts; import blackjack.model.gameresult.ProfitResult; import java.util.ArrayList; import java.util.HashMap; diff --git a/src/test/java/blackjack/model/BetAmountTest.java b/src/test/java/blackjack/model/BetAmountTest.java index 50f864dd992..0c6d2b2160f 100644 --- a/src/test/java/blackjack/model/BetAmountTest.java +++ b/src/test/java/blackjack/model/BetAmountTest.java @@ -2,6 +2,7 @@ import static org.junit.jupiter.api.Assertions.*; +import blackjack.model.bet.BetAmount; import blackjack.model.user.Player; import org.assertj.core.api.Assertions; import org.junit.jupiter.api.DisplayName; From ff2a3a1e5b2dd4e423d0bda1ab3f850096791e91 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Fri, 13 Mar 2026 13:42:40 +0900 Subject: [PATCH 68/81] =?UTF-8?q?refactor:=20=EC=B5=9C=EC=A2=85=20?= =?UTF-8?q?=EC=88=98=EC=9D=B5=20=EB=A1=9C=EC=A7=81=20=EC=B1=85=EC=9E=84=20?= =?UTF-8?q?=EB=B6=84=EB=A6=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/BlackjackGame.java | 13 ++-- .../controller/BlackjackController.java | 2 +- .../java/blackjack/model/bet/BetAmounts.java | 23 ++++--- .../model/gameresult/GameResult.java | 60 +++++++++++++++--- src/main/java/blackjack/model/user/Users.java | 62 ++++--------------- 5 files changed, 81 insertions(+), 79 deletions(-) diff --git a/src/main/java/blackjack/BlackjackGame.java b/src/main/java/blackjack/BlackjackGame.java index 369b0b58b59..7d7f98606f2 100644 --- a/src/main/java/blackjack/BlackjackGame.java +++ b/src/main/java/blackjack/BlackjackGame.java @@ -14,6 +14,7 @@ import java.util.HashMap; import java.util.List; import java.util.Map; +import java.util.function.Consumer; import java.util.function.Function; import java.util.function.Supplier; @@ -45,20 +46,18 @@ public void provideInitCards(Users users) { cardProvider.provideInitCards(users); } - public void hit(Users users, Function readHitCommand) { - List players = users.getPlayers(); - Dealer dealer = users.getDealer(); - - for (Player player : players) { + public void hit(Users users, Function readHitCommand, Consumer printPlayerCards, Runnable printDealerHit) { + for (Player player : users.getPlayers()) { while (retryUntilSuccess(() -> checkY(player, readHitCommand)) && checkAddCard(player)) { cardProvider.provideOneCard(player); - OutputView.printPlayerCards(player); + printPlayerCards.accept(player); } } + Dealer dealer = users.getDealer(); while (dealer.isHitAvailable()) { cardProvider.provideOneCard(dealer); - OutputView.printDealerHit(); + printDealerHit.run(); } } diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index 39179586422..bdcc0bd201f 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -26,7 +26,7 @@ public void run() { provideInitCardsAndPrint(users); - blackjackGame.hit(users, InputView::readHitCommand); + blackjackGame.hit(users, InputView::readHitCommand, OutputView::printPlayerCards, OutputView::printDealerHit); printHandStatus(users); diff --git a/src/main/java/blackjack/model/bet/BetAmounts.java b/src/main/java/blackjack/model/bet/BetAmounts.java index 6f058ae02c1..056183e3c06 100644 --- a/src/main/java/blackjack/model/bet/BetAmounts.java +++ b/src/main/java/blackjack/model/bet/BetAmounts.java @@ -1,5 +1,6 @@ package blackjack.model.bet; +import blackjack.model.gameresult.GameResult; import blackjack.model.user.Player; import java.util.Map; @@ -11,22 +12,20 @@ public BetAmounts(Map betAmounts) { this.betAmounts = betAmounts; } - public int calculateWinPayout(Player player) { + public int calculateProfit(Player player, GameResult gameResult) { BetAmount betAmount = betAmounts.get(player); - return betAmount.getAmount(); - } + if (gameResult == GameResult.BLACKJACK_WIN) { + return (int) Math.round(betAmount.getAmount() * 1.5); + } - public int calculateLosePayout(Player player) { - BetAmount betAmount = betAmounts.get(player); - return -betAmount.getAmount(); - } + if (gameResult == GameResult.WIN) { + return betAmount.getAmount(); + } - public int calculateBlackjackPayout(Player player) { - BetAmount betAmount = betAmounts.get(player); - return (int) Math.round(betAmount.getAmount() * 1.5); - } + if (gameResult == GameResult.LOSE) { + return -betAmount.getAmount(); + } - public int calculateDrawPayout() { return 0; } } diff --git a/src/main/java/blackjack/model/gameresult/GameResult.java b/src/main/java/blackjack/model/gameresult/GameResult.java index ce9e77c968b..e5426f2f8e9 100644 --- a/src/main/java/blackjack/model/gameresult/GameResult.java +++ b/src/main/java/blackjack/model/gameresult/GameResult.java @@ -1,19 +1,63 @@ package blackjack.model.gameresult; +import blackjack.model.user.Dealer; +import blackjack.model.user.Player; + public enum GameResult { - WIN("승"), - DRAW("무"), - LOSE("패"), + BLACKJACK_WIN, + WIN, + DRAW, + LOSE, ; - private final String format; + public static GameResult judge(Dealer dealer, Player player) { + if (player.isBust() || dealer.isBust()) { + return judgeByBust(dealer, player); + } + + if (player.isBlackjack() || dealer.isBlackjack()) { + return judgeByBlackjack(dealer, player); + } + + return judgeByScore(dealer, player); + } + + private static GameResult judgeByBust(Dealer dealer, Player player) { + if (player.isBust()) { + return LOSE; + } - GameResult(String format) { - this.format = format; + if (dealer.isBust()) { + return WIN; + } + return null; } - public String getFormat() { - return format; + private static GameResult judgeByBlackjack(Dealer dealer, Player player) { + if (player.isBlackjack() && dealer.isBlackjack()) { + return DRAW; + } + + if (player.isBlackjack()) { + return BLACKJACK_WIN; + } + + if (dealer.isBlackjack()) { + return LOSE; + } + return null; + } + + private static GameResult judgeByScore(Dealer dealer, Player player) { + if (player.totalScore() > dealer.totalScore()) { + return WIN; + } + + if (player.totalScore() < dealer.totalScore()) { + return LOSE; + } + + return DRAW; } } \ No newline at end of file diff --git a/src/main/java/blackjack/model/user/Users.java b/src/main/java/blackjack/model/user/Users.java index b45902b1a63..f3ed8e7e3c7 100644 --- a/src/main/java/blackjack/model/user/Users.java +++ b/src/main/java/blackjack/model/user/Users.java @@ -1,6 +1,7 @@ package blackjack.model.user; import blackjack.model.bet.BetAmounts; +import blackjack.model.gameresult.GameResult; import blackjack.model.gameresult.ProfitResult; import java.util.ArrayList; import java.util.HashMap; @@ -38,65 +39,24 @@ public Dealer getDealer() { .orElseThrow(() -> new IllegalArgumentException(ERROR_DEALER_NOT_FOUND)); } - public List getUsers() { - return List.copyOf(users); - } - public ProfitResult determineWinner(BetAmounts betAmounts) { Map result = new HashMap<>(); - int dealerPayout = 0; List players = getPlayers(); Dealer dealer = getDealer(); for (Player player : players) { - if (player.isBust()) { - result.put(player, betAmounts.calculateLosePayout(player)); - dealerPayout += betAmounts.calculateWinPayout(player); - continue; - } - - if (player.isBlackjack() && dealer.isBlackjack()) { - result.put(player, betAmounts.calculateDrawPayout()); - dealerPayout += betAmounts.calculateDrawPayout(); - continue; - } - - if (player.isBlackjack()) { - result.put(player, betAmounts.calculateBlackjackPayout(player)); - dealerPayout -= betAmounts.calculateBlackjackPayout(player); - continue; - } - - if (dealer.isBlackjack()) { - result.put(player, betAmounts.calculateLosePayout(player)); - dealerPayout += betAmounts.calculateWinPayout(player); - continue; - } - - if (dealer.isBust()) { - result.put(player, betAmounts.calculateWinPayout(player)); - dealerPayout -= betAmounts.calculateWinPayout(player); - continue; - } - - if (dealer.totalScore() == player.totalScore()) { - result.put(player, betAmounts.calculateDrawPayout()); - dealerPayout += betAmounts.calculateDrawPayout(); - continue; - } - - if (dealer.totalScore() > player.totalScore()) { - result.put(player, betAmounts.calculateLosePayout(player)); - dealerPayout += betAmounts.calculateWinPayout(player); - continue; - } - - if (dealer.totalScore() < player.totalScore()) { - result.put(player, betAmounts.calculateWinPayout(player)); - dealerPayout -= betAmounts.calculateWinPayout(player); - } + GameResult gameResult = GameResult.judge(dealer, player); + int profit = betAmounts.calculateProfit(player, gameResult); + result.put(player, profit); } + int dealerPayout = -getTotalPlayerProfit(result); return new ProfitResult(result, dealerPayout); } + + private static int getTotalPlayerProfit(Map result) { + return result.values().stream() + .mapToInt(Integer::intValue) + .sum(); + } } From 7174a930e26cc1fc2c2d3f72956abffafd769ce5 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Fri, 13 Mar 2026 13:47:19 +0900 Subject: [PATCH 69/81] =?UTF-8?q?refactor:=20=EA=B2=8C=EC=9E=84=20?= =?UTF-8?q?=EC=A2=85=EB=A3=8C=20=EB=A9=94=EC=84=9C=EB=93=9C=20BlackjackGam?= =?UTF-8?q?e=EC=9C=BC=EB=A1=9C=20=EC=9C=84=EC=9E=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/BlackjackGame.java | 4 ++++ src/main/java/blackjack/controller/BlackjackController.java | 2 +- 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/src/main/java/blackjack/BlackjackGame.java b/src/main/java/blackjack/BlackjackGame.java index 7d7f98606f2..d924736f757 100644 --- a/src/main/java/blackjack/BlackjackGame.java +++ b/src/main/java/blackjack/BlackjackGame.java @@ -65,6 +65,10 @@ public ProfitResult determineWinner(Users users, BetAmounts betAmounts) { return users.determineWinner(betAmounts); } + public void end(Runnable closeScanner) { + closeScanner.run(); + } + private boolean checkY(Player player, Function readHitCommand) { String input = readHitCommand.apply(player); HitCommand hitCommand = new HitCommand(input); diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index bdcc0bd201f..44f16424f9f 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -32,7 +32,7 @@ public void run() { printProfitResult(users, betAmounts); - InputView.closeScanner(); + blackjackGame.end(InputView::closeScanner); } private void provideInitCardsAndPrint(Users users) { From 104aea216dc0969e66c97a86574be5e1870e4983 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Fri, 13 Mar 2026 13:53:23 +0900 Subject: [PATCH 70/81] =?UTF-8?q?test:=20=EB=8B=A8=EC=9C=84=20=ED=85=8C?= =?UTF-8?q?=EC=8A=A4=ED=8A=B8=20=EC=9E=91=EC=84=B1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../model/{ => bet}/BetAmountTest.java | 3 +- .../blackjack/model/card/HitCommandTest.java | 29 +++++++++++++++++++ 2 files changed, 30 insertions(+), 2 deletions(-) rename src/test/java/blackjack/model/{ => bet}/BetAmountTest.java (96%) diff --git a/src/test/java/blackjack/model/BetAmountTest.java b/src/test/java/blackjack/model/bet/BetAmountTest.java similarity index 96% rename from src/test/java/blackjack/model/BetAmountTest.java rename to src/test/java/blackjack/model/bet/BetAmountTest.java index 0c6d2b2160f..da9d8e42cfd 100644 --- a/src/test/java/blackjack/model/BetAmountTest.java +++ b/src/test/java/blackjack/model/bet/BetAmountTest.java @@ -1,8 +1,7 @@ -package blackjack.model; +package blackjack.model.bet; import static org.junit.jupiter.api.Assertions.*; -import blackjack.model.bet.BetAmount; import blackjack.model.user.Player; import org.assertj.core.api.Assertions; import org.junit.jupiter.api.DisplayName; diff --git a/src/test/java/blackjack/model/card/HitCommandTest.java b/src/test/java/blackjack/model/card/HitCommandTest.java index 98c40690317..2e96da9b968 100644 --- a/src/test/java/blackjack/model/card/HitCommandTest.java +++ b/src/test/java/blackjack/model/card/HitCommandTest.java @@ -1,5 +1,6 @@ package blackjack.model.card; +import static org.assertj.core.api.Assertions.assertThat; import static org.assertj.core.api.Assertions.assertThatThrownBy; import static org.junit.jupiter.api.Assertions.assertDoesNotThrow; @@ -35,4 +36,32 @@ void create_hitCommand_fail_when_invalid_input(String invalidInput) { assertThatThrownBy(() -> new HitCommand(invalidInput)) .isInstanceOf(IllegalArgumentException.class); } + + @ParameterizedTest + @ValueSource(strings = {"y", "Y"}) + @DisplayName("입력값이 y 또는 Y일 경우 true 반환") + void isY_return_true_when_y_Y(String hitCommandInput) { + // given + HitCommand hitCommand = new HitCommand(hitCommandInput); + + //when + boolean result = hitCommand.isY(); + + // then + assertThat(result).isTrue(); + } + + @ParameterizedTest + @ValueSource(strings = {"n", "N"}) + @DisplayName("입력값이 n 또는 N일 경우 false 반환") + void isY_return_false_when_n_N(String hitCommandInput) { + // given + HitCommand hitCommand = new HitCommand(hitCommandInput); + + //when + boolean result = hitCommand.isY(); + + // then + assertThat(result).isFalse(); + } } \ No newline at end of file From 338152fa1c220438b82e4d4d1ae0436bcdca1097 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Fri, 13 Mar 2026 14:52:47 +0900 Subject: [PATCH 71/81] =?UTF-8?q?refactor:=20=ED=8C=8C=EB=9D=BC=EB=AF=B8?= =?UTF-8?q?=ED=84=B0=20=EA=B0=9C=EC=88=98=EB=A5=BC=20=EC=A4=84=EC=9D=B4?= =?UTF-8?q?=EA=B8=B0=20=EC=9C=84=ED=95=B4=20=EB=A9=94=EC=84=9C=EB=93=9C=20?= =?UTF-8?q?=EB=B6=84=EB=A6=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/BlackjackGame.java | 24 ++++++++++--------- .../controller/BlackjackController.java | 7 +++++- 2 files changed, 19 insertions(+), 12 deletions(-) diff --git a/src/main/java/blackjack/BlackjackGame.java b/src/main/java/blackjack/BlackjackGame.java index d924736f757..dcd5201475c 100644 --- a/src/main/java/blackjack/BlackjackGame.java +++ b/src/main/java/blackjack/BlackjackGame.java @@ -46,29 +46,31 @@ public void provideInitCards(Users users) { cardProvider.provideInitCards(users); } - public void hit(Users users, Function readHitCommand, Consumer printPlayerCards, Runnable printDealerHit) { - for (Player player : users.getPlayers()) { + public ProfitResult determineWinner(Users users, BetAmounts betAmounts) { + return users.determineWinner(betAmounts); + } + + public void end(Runnable closeScanner) { + closeScanner.run(); + } + + public void hitPlayers(List players, Function readHitCommand, + Consumer printPlayerCards) { + for (Player player : players) { while (retryUntilSuccess(() -> checkY(player, readHitCommand)) && checkAddCard(player)) { cardProvider.provideOneCard(player); printPlayerCards.accept(player); } } + } - Dealer dealer = users.getDealer(); + public void hitDealer(Dealer dealer, Runnable printDealerHit) { while (dealer.isHitAvailable()) { cardProvider.provideOneCard(dealer); printDealerHit.run(); } } - public ProfitResult determineWinner(Users users, BetAmounts betAmounts) { - return users.determineWinner(betAmounts); - } - - public void end(Runnable closeScanner) { - closeScanner.run(); - } - private boolean checkY(Player player, Function readHitCommand) { String input = readHitCommand.apply(player); HitCommand hitCommand = new HitCommand(input); diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index 44f16424f9f..39a42068f6d 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -26,7 +26,7 @@ public void run() { provideInitCardsAndPrint(users); - blackjackGame.hit(users, InputView::readHitCommand, OutputView::printPlayerCards, OutputView::printDealerHit); + hit(users); printHandStatus(users); @@ -40,6 +40,11 @@ private void provideInitCardsAndPrint(Users users) { OutputView.printInitCards(users); } + private void hit(Users users) { + blackjackGame.hitPlayers(users.getPlayers(), InputView::readHitCommand, OutputView::printPlayerCards); + blackjackGame.hitDealer(users.getDealer(), OutputView::printDealerHit); + } + private void printHandStatus(Users users) { OutputView.printHandStatus(users); } From c783fbb65e215a710992e858e9ca76574f93a8ca Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Fri, 13 Mar 2026 14:53:58 +0900 Subject: [PATCH 72/81] =?UTF-8?q?chore:=20=EB=A9=94=EC=84=9C=EB=93=9C=20?= =?UTF-8?q?=EC=88=9C=EC=84=9C=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/BlackjackGame.java | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/src/main/java/blackjack/BlackjackGame.java b/src/main/java/blackjack/BlackjackGame.java index dcd5201475c..8b916308898 100644 --- a/src/main/java/blackjack/BlackjackGame.java +++ b/src/main/java/blackjack/BlackjackGame.java @@ -46,14 +46,6 @@ public void provideInitCards(Users users) { cardProvider.provideInitCards(users); } - public ProfitResult determineWinner(Users users, BetAmounts betAmounts) { - return users.determineWinner(betAmounts); - } - - public void end(Runnable closeScanner) { - closeScanner.run(); - } - public void hitPlayers(List players, Function readHitCommand, Consumer printPlayerCards) { for (Player player : players) { @@ -71,6 +63,14 @@ public void hitDealer(Dealer dealer, Runnable printDealerHit) { } } + public ProfitResult determineWinner(Users users, BetAmounts betAmounts) { + return users.determineWinner(betAmounts); + } + + public void end(Runnable closeScanner) { + closeScanner.run(); + } + private boolean checkY(Player player, Function readHitCommand) { String input = readHitCommand.apply(player); HitCommand hitCommand = new HitCommand(input); From 5e46963bf712f7a5b895940d3b92104debfb1cee Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Fri, 13 Mar 2026 15:17:11 +0900 Subject: [PATCH 73/81] =?UTF-8?q?refactor:=20indent=202=20->=20indent=201?= =?UTF-8?q?=EB=A1=9C=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/BlackjackGame.java | 12 ++++++---- .../blackjack/model/card/CardProvider.java | 22 +++++++++++-------- src/main/java/blackjack/model/card/Hand.java | 14 +++++++----- 3 files changed, 29 insertions(+), 19 deletions(-) diff --git a/src/main/java/blackjack/BlackjackGame.java b/src/main/java/blackjack/BlackjackGame.java index 8b916308898..ea961acad73 100644 --- a/src/main/java/blackjack/BlackjackGame.java +++ b/src/main/java/blackjack/BlackjackGame.java @@ -49,10 +49,7 @@ public void provideInitCards(Users users) { public void hitPlayers(List players, Function readHitCommand, Consumer printPlayerCards) { for (Player player : players) { - while (retryUntilSuccess(() -> checkY(player, readHitCommand)) && checkAddCard(player)) { - cardProvider.provideOneCard(player); - printPlayerCards.accept(player); - } + hitPlayer(player, readHitCommand, printPlayerCards); } } @@ -71,6 +68,13 @@ public void end(Runnable closeScanner) { closeScanner.run(); } + private void hitPlayer(Player player, Function readHitCommand, Consumer printPlayerCards) { + while (retryUntilSuccess(() -> checkY(player, readHitCommand)) && checkAddCard(player)) { + cardProvider.provideOneCard(player); + printPlayerCards.accept(player); + } + } + private boolean checkY(Player player, Function readHitCommand) { String input = readHitCommand.apply(player); HitCommand hitCommand = new HitCommand(input); diff --git a/src/main/java/blackjack/model/card/CardProvider.java b/src/main/java/blackjack/model/card/CardProvider.java index cfe0225d345..b9a633f958c 100644 --- a/src/main/java/blackjack/model/card/CardProvider.java +++ b/src/main/java/blackjack/model/card/CardProvider.java @@ -5,10 +5,12 @@ import blackjack.model.user.User; import blackjack.model.user.Users; import java.util.ArrayList; +import java.util.Arrays; import java.util.Collections; import java.util.LinkedList; import java.util.List; import java.util.Queue; +import java.util.stream.Collectors; public class CardProvider { @@ -22,12 +24,10 @@ public CardProvider() { } private void initDeck() { - List cards = new ArrayList<>(); - for (Rank rank : Rank.values()) { - for (Suit suit : Suit.values()) { - cards.add(new Card(rank, suit)); - } - } + List cards = Arrays.stream(Rank.values()) + .flatMap(rank -> Arrays.stream(Suit.values()) + .map(suit -> new Card(rank, suit))) + .collect(Collectors.toCollection(ArrayList::new)); Collections.shuffle(cards); this.deck.addAll(cards); } @@ -36,13 +36,17 @@ public void provideInitCards(Users users) { List players = users.getPlayers(); Dealer dealer = users.getDealer(); for (int i = INIT_CARDS_START_IDX; i < INIT_CARDS_END_IDX; i++) { - for (Player player : players) { - provideOneCard(player); - } + provideOneCardToPlayers(players); provideOneCard(dealer); } } + private void provideOneCardToPlayers(List players) { + for (Player player : players) { + provideOneCard(player); + } + } + public void provideOneCard(User user) { if (deck.peek() == null) { initDeck(); diff --git a/src/main/java/blackjack/model/card/Hand.java b/src/main/java/blackjack/model/card/Hand.java index a17d84d9604..338b2234533 100644 --- a/src/main/java/blackjack/model/card/Hand.java +++ b/src/main/java/blackjack/model/card/Hand.java @@ -55,13 +55,15 @@ public int totalScore(List cards) { private int addAceScore(List aceCards, int totalScore) { for (int i = 0; i < aceCards.size(); i++) { - if (totalScore + ACE_SCORE_ELEVEN > BLACKJACK_SCORE) { - totalScore += ACE_SCORE_ONE; - continue; - } - totalScore += ACE_SCORE_ELEVEN; + totalScore += calculateAceScore(totalScore); } - return totalScore; } + + private static int calculateAceScore(int totalScore) { + if (totalScore + ACE_SCORE_ELEVEN > BLACKJACK_SCORE) { + return ACE_SCORE_ONE; + } + return ACE_SCORE_ELEVEN; + } } From 58be5be26d47ec3633b29cfdaafee96debf6a2ef Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Sun, 15 Mar 2026 10:53:27 +0900 Subject: [PATCH 74/81] =?UTF-8?q?refactor:=20null=20=EB=B0=98=ED=99=98?= =?UTF-8?q?=ED=95=98=EC=A7=80=20=EC=95=8A=EB=8F=84=EB=A1=9D=20=EB=A9=94?= =?UTF-8?q?=EC=84=9C=EB=93=9C=20=EA=B5=AC=EC=A1=B0=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../java/blackjack/model/gameresult/GameResult.java | 10 ++-------- 1 file changed, 2 insertions(+), 8 deletions(-) diff --git a/src/main/java/blackjack/model/gameresult/GameResult.java b/src/main/java/blackjack/model/gameresult/GameResult.java index e5426f2f8e9..35ed215d4db 100644 --- a/src/main/java/blackjack/model/gameresult/GameResult.java +++ b/src/main/java/blackjack/model/gameresult/GameResult.java @@ -28,10 +28,7 @@ private static GameResult judgeByBust(Dealer dealer, Player player) { return LOSE; } - if (dealer.isBust()) { - return WIN; - } - return null; + return WIN; } private static GameResult judgeByBlackjack(Dealer dealer, Player player) { @@ -43,10 +40,7 @@ private static GameResult judgeByBlackjack(Dealer dealer, Player player) { return BLACKJACK_WIN; } - if (dealer.isBlackjack()) { - return LOSE; - } - return null; + return LOSE; } private static GameResult judgeByScore(Dealer dealer, Player player) { From bb11f00d7f12c885f04c6c1b67588e97272e2b8b Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Sun, 15 Mar 2026 13:08:10 +0900 Subject: [PATCH 75/81] =?UTF-8?q?refactor:=20=EC=97=90=EB=9F=AC=20?= =?UTF-8?q?=EB=A9=94=EC=8B=9C=EC=A7=80=20=EB=82=B4=EC=9A=A9=20=EC=88=98?= =?UTF-8?q?=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/bet/BetAmount.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/blackjack/model/bet/BetAmount.java b/src/main/java/blackjack/model/bet/BetAmount.java index aa45d95d5e1..a8cc0a2d030 100644 --- a/src/main/java/blackjack/model/bet/BetAmount.java +++ b/src/main/java/blackjack/model/bet/BetAmount.java @@ -4,7 +4,7 @@ public class BetAmount { private static final String ERROR_EMPTY_INPUT = "입력값은 공백일 수 없습니다."; private static final String ERROR_BET_AMOUNT_NOT_INTEGER = "배팅 금액은 숫자 형태로 입력해야 합니다."; - private static final String ERROR_BET_AMOUNT_NOT_POSITIVE = "배팅 금액은 0 이상이어야 합니다."; + private static final String ERROR_BET_AMOUNT_NOT_POSITIVE = "배팅 금액은 1원 이상이어야 합니다."; private final int amount; From ee03f6c659f1201cff1b0079595b3cc46240a80b Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Sun, 15 Mar 2026 13:11:29 +0900 Subject: [PATCH 76/81] =?UTF-8?q?refactor:=20=EB=B0=A9=EC=96=B4=EC=A0=81?= =?UTF-8?q?=20=EB=B3=B5=EC=82=AC=20=EC=A0=81=EC=9A=A9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/bet/BetAmounts.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/blackjack/model/bet/BetAmounts.java b/src/main/java/blackjack/model/bet/BetAmounts.java index 056183e3c06..248f9bc83f7 100644 --- a/src/main/java/blackjack/model/bet/BetAmounts.java +++ b/src/main/java/blackjack/model/bet/BetAmounts.java @@ -9,7 +9,7 @@ public class BetAmounts { private final Map betAmounts; public BetAmounts(Map betAmounts) { - this.betAmounts = betAmounts; + this.betAmounts = Map.copyOf(betAmounts); } public int calculateProfit(Player player, GameResult gameResult) { From 26b13e7512d997a006c47a9f313132feb9484155 Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Sun, 15 Mar 2026 13:14:34 +0900 Subject: [PATCH 77/81] =?UTF-8?q?refactor:=20=EB=AF=B8=EC=82=AC=EC=9A=A9?= =?UTF-8?q?=20=ED=95=84=EB=93=9C,=20=EB=A9=94=EC=84=9C=EB=93=9C=20?= =?UTF-8?q?=EC=A0=9C=EA=B1=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/user/Dealer.java | 14 -------------- 1 file changed, 14 deletions(-) diff --git a/src/main/java/blackjack/model/user/Dealer.java b/src/main/java/blackjack/model/user/Dealer.java index d0fce4b9184..51b1d80d67c 100644 --- a/src/main/java/blackjack/model/user/Dealer.java +++ b/src/main/java/blackjack/model/user/Dealer.java @@ -1,25 +1,11 @@ package blackjack.model.user; -import blackjack.model.gameresult.GameResult; -import java.util.EnumMap; - public class Dealer extends User { private static final int DEALER_ADD_CARD_STAND = 17; - private final EnumMap gameResults; - public Dealer() { super("딜러"); - gameResults = new EnumMap<>(GameResult.class); - } - - public EnumMap getGameResults() { - return gameResults; - } - - public void addResult(GameResult gameResult) { - gameResults.merge(gameResult, 1, Integer::sum); } @Override From ad9f3b49c94759c63c2acb9211c6d0b8e212669c Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Sun, 15 Mar 2026 14:06:12 +0900 Subject: [PATCH 78/81] =?UTF-8?q?refactor:=20BlackjackGame=EC=97=90?= =?UTF-8?q?=EC=84=9C=20View=20=EC=B0=B8=EC=A1=B0=20=EC=A0=9C=EA=B1=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/BlackjackGame.java | 18 +++++++++++------- .../controller/BlackjackController.java | 3 ++- 2 files changed, 13 insertions(+), 8 deletions(-) diff --git a/src/main/java/blackjack/BlackjackGame.java b/src/main/java/blackjack/BlackjackGame.java index ea961acad73..3edb5d3671b 100644 --- a/src/main/java/blackjack/BlackjackGame.java +++ b/src/main/java/blackjack/BlackjackGame.java @@ -10,7 +10,6 @@ import blackjack.model.user.Dealer; import blackjack.model.user.Player; import blackjack.model.user.Users; -import blackjack.view.OutputView; import java.util.HashMap; import java.util.List; import java.util.Map; @@ -47,9 +46,9 @@ public void provideInitCards(Users users) { } public void hitPlayers(List players, Function readHitCommand, - Consumer printPlayerCards) { + Consumer printPlayerCards, Runnable printCantHit) { for (Player player : players) { - hitPlayer(player, readHitCommand, printPlayerCards); + hitPlayer(player, readHitCommand, printPlayerCards, printCantHit); } } @@ -68,8 +67,13 @@ public void end(Runnable closeScanner) { closeScanner.run(); } - private void hitPlayer(Player player, Function readHitCommand, Consumer printPlayerCards) { - while (retryUntilSuccess(() -> checkY(player, readHitCommand)) && checkAddCard(player)) { + private void hitPlayer(Player player, Function readHitCommand, Consumer printPlayerCards, + Runnable printCantHit) { + if (!isHitAvailable(player, printCantHit)) { + return; + } + + while (retryUntilSuccess(() -> checkY(player, readHitCommand))) { cardProvider.provideOneCard(player); printPlayerCards.accept(player); } @@ -81,11 +85,11 @@ private boolean checkY(Player player, Function readHitCommand) { return hitCommand.isY(); } - private boolean checkAddCard(Player player) { + private boolean isHitAvailable(Player player, Runnable printCantHit) { if (player.isHitAvailable()) { return true; } - OutputView.printCantHit(); + printCantHit.run(); return false; } } diff --git a/src/main/java/blackjack/controller/BlackjackController.java b/src/main/java/blackjack/controller/BlackjackController.java index 39a42068f6d..f2e571b9894 100644 --- a/src/main/java/blackjack/controller/BlackjackController.java +++ b/src/main/java/blackjack/controller/BlackjackController.java @@ -41,7 +41,8 @@ private void provideInitCardsAndPrint(Users users) { } private void hit(Users users) { - blackjackGame.hitPlayers(users.getPlayers(), InputView::readHitCommand, OutputView::printPlayerCards); + blackjackGame.hitPlayers(users.getPlayers(), InputView::readHitCommand, OutputView::printPlayerCards, + OutputView::printCantHit); blackjackGame.hitDealer(users.getDealer(), OutputView::printDealerHit); } From fdf622c52c247f553b901416e8b0f75c6262ac9b Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Sun, 15 Mar 2026 14:10:04 +0900 Subject: [PATCH 79/81] =?UTF-8?q?test:=20=EB=AF=B8=EC=82=AC=EC=9A=A9=20?= =?UTF-8?q?=EB=B3=80=EC=88=98=20=EB=B0=8F=20=EC=A4=91=EB=B3=B5=20=ED=85=8C?= =?UTF-8?q?=EC=8A=A4=ED=8A=B8=20=ED=81=B4=EB=9E=98=EC=8A=A4=20=EC=A0=9C?= =?UTF-8?q?=EA=B1=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../blackjack/model/CardProviderTest.java | 43 ------------- src/test/java/blackjack/model/HandTest.java | 63 ------------------- .../java/blackjack/model/HitCommandTest.java | 43 ------------- .../blackjack/model/bet/BetAmountTest.java | 12 ---- 4 files changed, 161 deletions(-) delete mode 100644 src/test/java/blackjack/model/CardProviderTest.java delete mode 100644 src/test/java/blackjack/model/HandTest.java delete mode 100644 src/test/java/blackjack/model/HitCommandTest.java diff --git a/src/test/java/blackjack/model/CardProviderTest.java b/src/test/java/blackjack/model/CardProviderTest.java deleted file mode 100644 index 6f086bf4530..00000000000 --- a/src/test/java/blackjack/model/CardProviderTest.java +++ /dev/null @@ -1,43 +0,0 @@ -package blackjack.model; - -import static org.assertj.core.api.Assertions.assertThat; - -import blackjack.model.card.CardProvider; -import blackjack.model.user.Dealer; -import blackjack.model.user.Player; -import blackjack.model.user.Users; -import java.util.List; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -class CardProviderTest { - - @Test - @DisplayName("딜러 및 플레이어에게 초기 카드 2장 정상 배분") - void test_provide_init_cards() { - CardProvider cardProvider = new CardProvider(); - - List players = List.of(new Player("pobi"), new Player("james")); - Dealer dealer = new Dealer(); - Users users = new Users(players, dealer); - - cardProvider.provideInitCards(users); - - for (Player player : players) { - assertThat(player.cards().size()).isEqualTo(2); - } - assertThat(dealer.cards().size()).isEqualTo(2); - } - - @Test - @DisplayName("카드 추가 지급 성공") - void test_provide_one_card_success() { - Player player = new Player("pobi"); - CardProvider cardProvider = new CardProvider(); - - cardProvider.provideOneCard(player); - - assertThat(player.cards().size()).isEqualTo(1); - } - -} \ No newline at end of file diff --git a/src/test/java/blackjack/model/HandTest.java b/src/test/java/blackjack/model/HandTest.java deleted file mode 100644 index 0fa5ef4c795..00000000000 --- a/src/test/java/blackjack/model/HandTest.java +++ /dev/null @@ -1,63 +0,0 @@ -package blackjack.model; - -import static org.assertj.core.api.Assertions.assertThat; - -import blackjack.model.card.Card; -import blackjack.model.card.Hand; -import blackjack.model.card.Rank; -import blackjack.model.card.Suit; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -class HandTest { - - @Test - @DisplayName("Hand가 블랙잭일 경우 true 반환") - void isBlackjack_return_true() { - //given - Hand hand = new Hand(); - hand.addCard(new Card(Rank.J, Suit.DIAMOND)); - hand.addCard(new Card(Rank.ACE, Suit.DIAMOND)); - - //when & then - assertThat(hand.isBlackjack()).isTrue(); - } - - @Test - @DisplayName("Hand가 블랙잭이 아닐 경우 false 반환") - void isBlackjack_return_false() { - //given - Hand hand = new Hand(); - hand.addCard(new Card(Rank.J, Suit.DIAMOND)); - hand.addCard(new Card(Rank.K, Suit.DIAMOND)); - - //when & then - assertThat(hand.isBlackjack()).isFalse(); - } - - @Test - @DisplayName("Hand가 버스트일 경우 true 반환") - void isBust_return_true() { - //given - Hand hand = new Hand(); - hand.addCard(new Card(Rank.J, Suit.DIAMOND)); - hand.addCard(new Card(Rank.Q, Suit.DIAMOND)); - hand.addCard(new Card(Rank.TWO, Suit.DIAMOND)); - - //when & then - assertThat(hand.isBust()).isTrue(); - } - - @Test - @DisplayName("Hand가 버스트가 아닐 경우 false 반환") - void isBust_return_false() { - //given - Hand hand = new Hand(); - hand.addCard(new Card(Rank.J, Suit.DIAMOND)); - hand.addCard(new Card(Rank.Q, Suit.DIAMOND)); - hand.addCard(new Card(Rank.ACE, Suit.DIAMOND)); - - //when & then - assertThat(hand.isBust()).isFalse(); - } -} \ No newline at end of file diff --git a/src/test/java/blackjack/model/HitCommandTest.java b/src/test/java/blackjack/model/HitCommandTest.java deleted file mode 100644 index 930073a4ddd..00000000000 --- a/src/test/java/blackjack/model/HitCommandTest.java +++ /dev/null @@ -1,43 +0,0 @@ -package blackjack.model; - -import static blackjack.model.constant.ErrorMessage.ERROR_EMPTY_INPUT; -import static blackjack.model.constant.ErrorMessage.ERROR_NOT_Y_N_INPUT; -import static org.assertj.core.api.Assertions.assertThatThrownBy; -import static org.junit.jupiter.api.Assertions.assertDoesNotThrow; - -import blackjack.model.card.HitCommand; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.ValueSource; - -class HitCommandTest { - - @ParameterizedTest - @ValueSource(strings = {"y", "Y", "n", "N"}) - @DisplayName("HitCommand 정상 생성") - void create_hitCommand_success(String hitCommand) { - //when & then - assertDoesNotThrow(() -> new HitCommand(hitCommand)); - } - - - @ParameterizedTest - @ValueSource(strings = {"", " "}) - @DisplayName("공백이 입력될 경우 예외 발생") - void create_hitCommand_fail_when_empty_input(String emptyInput) { - //when & then - assertThatThrownBy(() -> new HitCommand(emptyInput)) - .isInstanceOf(IllegalArgumentException.class) - .hasMessage(ERROR_EMPTY_INPUT.getErrorMessage()); - } - - @ParameterizedTest - @ValueSource(strings = {"ad", "y*"}) - @DisplayName("정해진 입력 외의 문자열을 입력할 경우 예외 발생") - void create_hitCommand_fail_when_invalid_input(String invalidInput) { - //when & then - assertThatThrownBy(() -> new HitCommand(invalidInput)) - .isInstanceOf(IllegalArgumentException.class) - .hasMessage(ERROR_NOT_Y_N_INPUT.getErrorMessage()); - } -} \ No newline at end of file diff --git a/src/test/java/blackjack/model/bet/BetAmountTest.java b/src/test/java/blackjack/model/bet/BetAmountTest.java index da9d8e42cfd..a26c3d08bfe 100644 --- a/src/test/java/blackjack/model/bet/BetAmountTest.java +++ b/src/test/java/blackjack/model/bet/BetAmountTest.java @@ -14,9 +14,6 @@ class BetAmountTest { @ValueSource(strings = {"1", "10"}) @DisplayName("배팅 금액 정상 생성") void createBetAmount_success(String input) { - // given - Player player = new Player("name"); - //when & then assertDoesNotThrow(() -> new BetAmount(input)); } @@ -25,9 +22,6 @@ void createBetAmount_success(String input) { @ValueSource(strings = {"", " "}) @DisplayName("입력값이 공백일 경우 예외 발생") void createBetAmount_fail_when_input_is_empty(String emptyInput) { - // given - Player player = new Player("name"); - //when & then Assertions.assertThatThrownBy(() -> new BetAmount(emptyInput)) .isInstanceOf(IllegalArgumentException.class); @@ -37,9 +31,6 @@ void createBetAmount_fail_when_input_is_empty(String emptyInput) { @ValueSource(strings = {"a", "1a", "123*"}) @DisplayName("입력값이 숫자 형태가 아닐 경우 예외 발생") void createBetAmount_fail_when_input_is_not_number(String stringInput) { - // given - Player player = new Player("name"); - //when & then Assertions.assertThatThrownBy(() -> new BetAmount(stringInput)) .isInstanceOf(IllegalArgumentException.class); @@ -49,9 +40,6 @@ void createBetAmount_fail_when_input_is_not_number(String stringInput) { @ValueSource(strings = {"0", "-1"}) @DisplayName("입력값이 양수가 아닐 경우 예외 발생") void createBetAmount_fail_when_input_is_not_positive(String negativeInput) { - // given - Player player = new Player("name"); - //when & then Assertions.assertThatThrownBy(() -> new BetAmount(negativeInput)) .isInstanceOf(IllegalArgumentException.class); From 6fe7b0b7755a4bdf21865804ba98e9f2ff34e17d Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Sun, 15 Mar 2026 14:16:02 +0900 Subject: [PATCH 80/81] =?UTF-8?q?refactor:=20=EB=AF=B8=EC=82=AC=EC=9A=A9?= =?UTF-8?q?=20=ED=8C=8C=EB=9D=BC=EB=AF=B8=ED=84=B0=20=EC=A0=9C=EA=B1=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/blackjack/model/gameresult/GameResult.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/blackjack/model/gameresult/GameResult.java b/src/main/java/blackjack/model/gameresult/GameResult.java index 35ed215d4db..778c7bf9ead 100644 --- a/src/main/java/blackjack/model/gameresult/GameResult.java +++ b/src/main/java/blackjack/model/gameresult/GameResult.java @@ -13,7 +13,7 @@ public enum GameResult { public static GameResult judge(Dealer dealer, Player player) { if (player.isBust() || dealer.isBust()) { - return judgeByBust(dealer, player); + return judgeByBust(player); } if (player.isBlackjack() || dealer.isBlackjack()) { @@ -23,7 +23,7 @@ public static GameResult judge(Dealer dealer, Player player) { return judgeByScore(dealer, player); } - private static GameResult judgeByBust(Dealer dealer, Player player) { + private static GameResult judgeByBust(Player player) { if (player.isBust()) { return LOSE; } From e36f7b42a4cf645a3d8cdefe6110819d8db730ed Mon Sep 17 00:00:00 2001 From: Chocoding1 Date: Sun, 15 Mar 2026 18:14:15 +0900 Subject: [PATCH 81/81] =?UTF-8?q?refactor:=20=EC=8A=B9=ED=8C=A8=20?= =?UTF-8?q?=ED=8C=90=EC=A0=95=20=EB=A1=9C=EC=A7=81=20Player=EB=A1=9C=20?= =?UTF-8?q?=EC=9D=B4=EB=8F=99?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../java/blackjack/model/bet/BetAmounts.java | 18 +----- .../blackjack/model/constant/Constant.java | 14 ----- .../model/constant/ErrorMessage.java | 19 ------- .../model/gameresult/GameResult.java | 55 ++++--------------- .../java/blackjack/model/user/Player.java | 48 ++++++++++++++++ src/main/java/blackjack/model/user/Users.java | 4 +- 6 files changed, 62 insertions(+), 96 deletions(-) delete mode 100644 src/main/java/blackjack/model/constant/Constant.java delete mode 100644 src/main/java/blackjack/model/constant/ErrorMessage.java diff --git a/src/main/java/blackjack/model/bet/BetAmounts.java b/src/main/java/blackjack/model/bet/BetAmounts.java index 248f9bc83f7..aa0015e89ab 100644 --- a/src/main/java/blackjack/model/bet/BetAmounts.java +++ b/src/main/java/blackjack/model/bet/BetAmounts.java @@ -1,6 +1,5 @@ package blackjack.model.bet; -import blackjack.model.gameresult.GameResult; import blackjack.model.user.Player; import java.util.Map; @@ -12,20 +11,7 @@ public BetAmounts(Map betAmounts) { this.betAmounts = Map.copyOf(betAmounts); } - public int calculateProfit(Player player, GameResult gameResult) { - BetAmount betAmount = betAmounts.get(player); - if (gameResult == GameResult.BLACKJACK_WIN) { - return (int) Math.round(betAmount.getAmount() * 1.5); - } - - if (gameResult == GameResult.WIN) { - return betAmount.getAmount(); - } - - if (gameResult == GameResult.LOSE) { - return -betAmount.getAmount(); - } - - return 0; + public BetAmount findByPlayer(Player player) { + return betAmounts.get(player); } } diff --git a/src/main/java/blackjack/model/constant/Constant.java b/src/main/java/blackjack/model/constant/Constant.java deleted file mode 100644 index f2389f6895d..00000000000 --- a/src/main/java/blackjack/model/constant/Constant.java +++ /dev/null @@ -1,14 +0,0 @@ -package blackjack.model.constant; - -public class Constant { - - public static final int DEALER_ADD_CARD_STAND = 17; - public static final int BLACKJACK_SCORE = 21; - - public static final int INIT_CARDS_START_IDX = 0; - public static final int INIT_CARDS_END_IDX = 2; - - public static final int ACE_SCORE_ONE = 1; - public static final int ACE_SCORE_ELEVEN = 11; - -} diff --git a/src/main/java/blackjack/model/constant/ErrorMessage.java b/src/main/java/blackjack/model/constant/ErrorMessage.java deleted file mode 100644 index 7aa3f071b21..00000000000 --- a/src/main/java/blackjack/model/constant/ErrorMessage.java +++ /dev/null @@ -1,19 +0,0 @@ -package blackjack.model.constant; - -public enum ErrorMessage { - - ERROR_EMPTY_INPUT("입력값은 공백일 수 없습니다."), - ERROR_NOT_Y_N_INPUT("입력값은 y 또는 n만 가능합니다."), - ERROR_INVALID_PLAYER_NAME("플레이어의 이름은 영어 or 한글로만 이루어질 수 있습니다."), - ; - - private final String errorMessage; - - ErrorMessage(String errorMessage) { - this.errorMessage = errorMessage; - } - - public String getErrorMessage() { - return errorMessage; - } -} diff --git a/src/main/java/blackjack/model/gameresult/GameResult.java b/src/main/java/blackjack/model/gameresult/GameResult.java index 778c7bf9ead..971eeb4e916 100644 --- a/src/main/java/blackjack/model/gameresult/GameResult.java +++ b/src/main/java/blackjack/model/gameresult/GameResult.java @@ -1,57 +1,22 @@ package blackjack.model.gameresult; -import blackjack.model.user.Dealer; -import blackjack.model.user.Player; +import blackjack.model.bet.BetAmount; public enum GameResult { - BLACKJACK_WIN, - WIN, - DRAW, - LOSE, + BLACKJACK_WIN(1.5), + WIN(1), + DRAW(0), + LOSE(-1), ; - public static GameResult judge(Dealer dealer, Player player) { - if (player.isBust() || dealer.isBust()) { - return judgeByBust(player); - } + private final double payoutRate; - if (player.isBlackjack() || dealer.isBlackjack()) { - return judgeByBlackjack(dealer, player); - } - - return judgeByScore(dealer, player); - } - - private static GameResult judgeByBust(Player player) { - if (player.isBust()) { - return LOSE; - } - - return WIN; - } - - private static GameResult judgeByBlackjack(Dealer dealer, Player player) { - if (player.isBlackjack() && dealer.isBlackjack()) { - return DRAW; - } - - if (player.isBlackjack()) { - return BLACKJACK_WIN; - } - - return LOSE; + GameResult(double payoutRate) { + this.payoutRate = payoutRate; } - private static GameResult judgeByScore(Dealer dealer, Player player) { - if (player.totalScore() > dealer.totalScore()) { - return WIN; - } - - if (player.totalScore() < dealer.totalScore()) { - return LOSE; - } - - return DRAW; + public int calculateProfit(BetAmount betAmount) { + return (int) Math.round(betAmount.getAmount() * this.payoutRate); } } \ No newline at end of file diff --git a/src/main/java/blackjack/model/user/Player.java b/src/main/java/blackjack/model/user/Player.java index 8c3901d00ab..e4169480162 100644 --- a/src/main/java/blackjack/model/user/Player.java +++ b/src/main/java/blackjack/model/user/Player.java @@ -1,5 +1,9 @@ package blackjack.model.user; +import static blackjack.model.gameresult.GameResult.*; + +import blackjack.model.gameresult.GameResult; + public class Player extends User { private static final int BLACKJACK_SCORE = 21; @@ -12,4 +16,48 @@ public Player(String name) { public boolean isHitAvailable() { return totalScore() < BLACKJACK_SCORE; } + + public GameResult judge(Dealer dealer) { + if (this.isBust() || dealer.isBust()) { + return judgeByBust(); + } + + if (this.isBlackjack() || dealer.isBlackjack()) { + return judgeByBlackjack(dealer); + } + + return judgeByScore(dealer); + } + + private GameResult judgeByBust() { + if (this.isBust()) { + return LOSE; + } + + return WIN; + } + + private GameResult judgeByBlackjack(Dealer dealer) { + if (this.isBlackjack() && dealer.isBlackjack()) { + return DRAW; + } + + if (this.isBlackjack()) { + return BLACKJACK_WIN; + } + + return LOSE; + } + + private GameResult judgeByScore(Dealer dealer) { + if (this.totalScore() > dealer.totalScore()) { + return WIN; + } + + if (this.totalScore() < dealer.totalScore()) { + return LOSE; + } + + return DRAW; + } } diff --git a/src/main/java/blackjack/model/user/Users.java b/src/main/java/blackjack/model/user/Users.java index f3ed8e7e3c7..9c1779e1c99 100644 --- a/src/main/java/blackjack/model/user/Users.java +++ b/src/main/java/blackjack/model/user/Users.java @@ -45,8 +45,8 @@ public ProfitResult determineWinner(BetAmounts betAmounts) { Dealer dealer = getDealer(); for (Player player : players) { - GameResult gameResult = GameResult.judge(dealer, player); - int profit = betAmounts.calculateProfit(player, gameResult); + GameResult gameResult = player.judge(dealer); + int profit = gameResult.calculateProfit(betAmounts.findByPlayer(player)); result.put(player, profit); } int dealerPayout = -getTotalPlayerProfit(result);