From 92c79ce4b0d07ea996448d80d006b8c956b74d88 Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Mon, 30 Mar 2026 23:07:54 +0900 Subject: [PATCH 01/22] =?UTF-8?q?=EA=B8=B0=EB=8A=A5=EC=9A=94=EA=B5=AC?= =?UTF-8?q?=EC=82=AC=ED=95=AD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- docs/README.md | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/docs/README.md b/docs/README.md index e69de29..8f261c2 100644 --- a/docs/README.md +++ b/docs/README.md @@ -0,0 +1,15 @@ +# 자동차 경주 게임 기능 목록 + +## 기능요구사항 +- [ ] 자동차 이름을 쉼표(,) 기준으로 구분하여 입력받기 +- [ ] 각 자동차에 이름을 부여하기 (5자 이하 검증) +- [ ] 시도할 횟수 입력받기 +- [ ] 0~9 사이의 무작위 값을 구하여 4 이상일 경우 전진하기 +- [ ] 차수별 실행 결과 출력하기 (이름 : ---) +- [ ] 우승자 판별 및 출력하기 (공동 우승 시 쉼표로 구분) + +## ⚠️ 예외 처리 +- [ ] 자동차 이름이 5자를 초과하는 경우 +- [ ] 자동차 이름이 빈 값인 경우 +- [ ] 시도 횟수가 숫자가 아닌 경우 +- [ ] 시도 횟수가 음수인 경우 \ No newline at end of file From fe56b854bab2b2931420b1b4cfde6bbce88fa2fc Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Mon, 30 Mar 2026 23:09:58 +0900 Subject: [PATCH 02/22] =?UTF-8?q?=EC=9E=90=EB=8F=99=EC=B0=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/Application.java | 36 ++++++++++++++++++++++++ 1 file changed, 36 insertions(+) diff --git a/src/main/java/racingcar/Application.java b/src/main/java/racingcar/Application.java index a17a52e..504a5c2 100644 --- a/src/main/java/racingcar/Application.java +++ b/src/main/java/racingcar/Application.java @@ -5,3 +5,39 @@ public static void main(String[] args) { // TODO: 프로그램 구현 } } +package racingcar; + +public class Car { + private final String name; + private int position = 0; + + public Car(String name) { + validateName(name); + this.name = name; + } + + private void validateName(String name) { + if (name == null || name.isBlank() || name.length() > 5) { + throw new IllegalArgumentException("자동차 이름은 1자 이상 5자 이하만 가능합니다."); + } + } + + public void move(int number) { + if (number >= 4) { + position++; + } + } + + public String getName() { + return name; + } + + public int getPosition() { + return position; + } + + // 현재 위치를 "-"로 변환하여 출력 형식 반환 + public String getStatusString() { + return name + " : " + "-".repeat(position); + } +} \ No newline at end of file From 22a1925f74c138ae69b1308840c6a1500609ee5e Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Mon, 30 Mar 2026 23:18:18 +0900 Subject: [PATCH 03/22] =?UTF-8?q?=EC=9E=90=EB=8F=99=EC=B0=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/Application.java | 39 --------------------- src/main/java/racingcar/Car.java | 43 ++++++++++++++++++++++++ 2 files changed, 43 insertions(+), 39 deletions(-) create mode 100644 src/main/java/racingcar/Car.java diff --git a/src/main/java/racingcar/Application.java b/src/main/java/racingcar/Application.java index 504a5c2..50ed5fb 100644 --- a/src/main/java/racingcar/Application.java +++ b/src/main/java/racingcar/Application.java @@ -1,43 +1,4 @@ package racingcar; public class Application { - public static void main(String[] args) { - // TODO: 프로그램 구현 - } } -package racingcar; - -public class Car { - private final String name; - private int position = 0; - - public Car(String name) { - validateName(name); - this.name = name; - } - - private void validateName(String name) { - if (name == null || name.isBlank() || name.length() > 5) { - throw new IllegalArgumentException("자동차 이름은 1자 이상 5자 이하만 가능합니다."); - } - } - - public void move(int number) { - if (number >= 4) { - position++; - } - } - - public String getName() { - return name; - } - - public int getPosition() { - return position; - } - - // 현재 위치를 "-"로 변환하여 출력 형식 반환 - public String getStatusString() { - return name + " : " + "-".repeat(position); - } -} \ No newline at end of file diff --git a/src/main/java/racingcar/Car.java b/src/main/java/racingcar/Car.java new file mode 100644 index 0000000..504a5c2 --- /dev/null +++ b/src/main/java/racingcar/Car.java @@ -0,0 +1,43 @@ +package racingcar; + +public class Application { + public static void main(String[] args) { + // TODO: 프로그램 구현 + } +} +package racingcar; + +public class Car { + private final String name; + private int position = 0; + + public Car(String name) { + validateName(name); + this.name = name; + } + + private void validateName(String name) { + if (name == null || name.isBlank() || name.length() > 5) { + throw new IllegalArgumentException("자동차 이름은 1자 이상 5자 이하만 가능합니다."); + } + } + + public void move(int number) { + if (number >= 4) { + position++; + } + } + + public String getName() { + return name; + } + + public int getPosition() { + return position; + } + + // 현재 위치를 "-"로 변환하여 출력 형식 반환 + public String getStatusString() { + return name + " : " + "-".repeat(position); + } +} \ No newline at end of file From ee8c6d81b8c9655402b54447531c18359706b333 Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Mon, 30 Mar 2026 23:20:39 +0900 Subject: [PATCH 04/22] =?UTF-8?q?=EC=8B=A4=ED=96=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/Car.java | 72 ++++++++++++++++++++++++++++++++ 1 file changed, 72 insertions(+) diff --git a/src/main/java/racingcar/Car.java b/src/main/java/racingcar/Car.java index 504a5c2..e64e526 100644 --- a/src/main/java/racingcar/Car.java +++ b/src/main/java/racingcar/Car.java @@ -40,4 +40,76 @@ public int getPosition() { public String getStatusString() { return name + " : " + "-".repeat(position); } +} +package racingcar; + +import camp.nextstep.edu.missionutils.Console; +import camp.nextstep.edu.missionutils.Randoms; +import java.util.ArrayList; +import java.util.List; +import java.util.StringJoiner; + +public class Application { + public static void main(String[] args) { + System.out.println("경주할 자동차 이름을 입력하세요.(이름은 쉼표(,) 기준으로 구분)"); + String[] names = Console.readLine().split(","); + List cars = createCars(names); + + System.out.println("시도할 회수는 몇회인가요?"); + int tryCount = parseTryCount(Console.readLine()); + + System.out.println("\n실행 결과"); + for (int i = 0; i < tryCount; i++) { + playOneRound(cars); + System.out.println(); + } + + printFinalWinners(cars); + } + + private static List createCars(String[] names) { + List cars = new ArrayList<>(); + for (String name : names) { + cars.add(new Car(name.trim())); + } + return cars; + } + + private static int parseTryCount(String input) { + try { + int count = Integer.parseInt(input); + if (count < 0) { + throw new IllegalArgumentException("시도 회수는 0 이상이어야 합니다."); + } + return count; + } catch (NumberFormatException e) { + throw new IllegalArgumentException("시도 회수는 숫자여야 합니다."); + } + } + + private static void playOneRound(List cars) { + for (Car car : cars) { + car.move(Randoms.pickNumberInRange(0, 9)); + System.out.println(car.getStatusString()); + } + } + + private static void printFinalWinners(List cars) { + int maxPosition = 0; + for (Car car : cars) { + maxPosition = Math.max(maxPosition, car.getPosition()); + } + + StringJoiner winners = new StringJoiner(", "); + for (Car car : cars) { + addWinner(winners, car, maxPosition); + } + System.out.println("최종 우승자 : " + winners.toString()); + } + + private static void addWinner(StringJoiner winners, Car car, int maxPosition) { + if (car.getPosition() == maxPosition) { + winners.add(car.getName()); + } + } } \ No newline at end of file From 6b491db95b8a287fee4006354a02536ce3a30626 Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Mon, 30 Mar 2026 23:24:06 +0900 Subject: [PATCH 05/22] =?UTF-8?q?=EC=8B=A4=ED=96=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/Application.java | 66 ++++++++++++++++++++++ src/main/java/racingcar/Car.java | 72 ------------------------ 2 files changed, 66 insertions(+), 72 deletions(-) diff --git a/src/main/java/racingcar/Application.java b/src/main/java/racingcar/Application.java index 50ed5fb..a5a42a1 100644 --- a/src/main/java/racingcar/Application.java +++ b/src/main/java/racingcar/Application.java @@ -2,3 +2,69 @@ public class Application { } +package racingcar; + +import camp.nextstep.edu.missionutils.Console; +import camp.nextstep.edu.missionutils.Randoms; +import java.util.ArrayList; +import java.util.List; +import java.util.StringJoiner; + +public class Application { + public static void main(String[] args) { + System.out.println("경주할 자동차 이름을 입력하세요.(이름은 쉼표(,) 기준으로 구분)"); + String[] names = Console.readLine().split(","); + List cars = createCars(names); + + System.out.println("시도할 회수는 몇회인가요?"); + int tryCount = parseTryCount(Console.readLine()); + + System.out.println("\n실행 결과"); + for (int i = 0; i < tryCount; i++) { + playOneRound(cars); + System.out.println(); + } + + printFinalWinners(cars); + } + + private static List createCars(String[] names) { + List cars = new ArrayList<>(); + for (String name : names) { + cars.add(new Car(name.trim())); + } + return cars; + } + + private static int parseTryCount(String input) { + try { + int count = Integer.parseInt(input); + if (count < 0) throw new IllegalArgumentException(); + return count; + } catch (NumberFormatException e) { + throw new IllegalArgumentException("숫자만 입력 가능합니다."); + } + } + + private static void playOneRound(List cars) { + for (Car car : cars) { + car.move(Randoms.pickNumberInRange(0, 9)); + System.out.println(car.getStatusString()); + } + } + + private static void printFinalWinners(List cars) { + int maxPosition = 0; + for (Car car : cars) { + maxPosition = Math.max(maxPosition, car.getPosition()); + } + + StringJoiner winners = new StringJoiner(", "); + for (Car car : cars) { + if (car.getPosition() == maxPosition) { + winners.add(car.getName()); + } + } + System.out.println("최종 우승자 : " + winners.toString()); + } +} \ No newline at end of file diff --git a/src/main/java/racingcar/Car.java b/src/main/java/racingcar/Car.java index e64e526..e17cdb3 100644 --- a/src/main/java/racingcar/Car.java +++ b/src/main/java/racingcar/Car.java @@ -41,75 +41,3 @@ public String getStatusString() { return name + " : " + "-".repeat(position); } } -package racingcar; - -import camp.nextstep.edu.missionutils.Console; -import camp.nextstep.edu.missionutils.Randoms; -import java.util.ArrayList; -import java.util.List; -import java.util.StringJoiner; - -public class Application { - public static void main(String[] args) { - System.out.println("경주할 자동차 이름을 입력하세요.(이름은 쉼표(,) 기준으로 구분)"); - String[] names = Console.readLine().split(","); - List cars = createCars(names); - - System.out.println("시도할 회수는 몇회인가요?"); - int tryCount = parseTryCount(Console.readLine()); - - System.out.println("\n실행 결과"); - for (int i = 0; i < tryCount; i++) { - playOneRound(cars); - System.out.println(); - } - - printFinalWinners(cars); - } - - private static List createCars(String[] names) { - List cars = new ArrayList<>(); - for (String name : names) { - cars.add(new Car(name.trim())); - } - return cars; - } - - private static int parseTryCount(String input) { - try { - int count = Integer.parseInt(input); - if (count < 0) { - throw new IllegalArgumentException("시도 회수는 0 이상이어야 합니다."); - } - return count; - } catch (NumberFormatException e) { - throw new IllegalArgumentException("시도 회수는 숫자여야 합니다."); - } - } - - private static void playOneRound(List cars) { - for (Car car : cars) { - car.move(Randoms.pickNumberInRange(0, 9)); - System.out.println(car.getStatusString()); - } - } - - private static void printFinalWinners(List cars) { - int maxPosition = 0; - for (Car car : cars) { - maxPosition = Math.max(maxPosition, car.getPosition()); - } - - StringJoiner winners = new StringJoiner(", "); - for (Car car : cars) { - addWinner(winners, car, maxPosition); - } - System.out.println("최종 우승자 : " + winners.toString()); - } - - private static void addWinner(StringJoiner winners, Car car, int maxPosition) { - if (car.getPosition() == maxPosition) { - winners.add(car.getName()); - } - } -} \ No newline at end of file From 53d61e3184b891520bbfa9161b46d35363beb154 Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Mon, 30 Mar 2026 23:35:06 +0900 Subject: [PATCH 06/22] =?UTF-8?q?=EC=8B=A4=ED=96=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/Application.java | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/src/main/java/racingcar/Application.java b/src/main/java/racingcar/Application.java index a5a42a1..160a28f 100644 --- a/src/main/java/racingcar/Application.java +++ b/src/main/java/racingcar/Application.java @@ -1,9 +1,5 @@ package racingcar; -public class Application { -} -package racingcar; - import camp.nextstep.edu.missionutils.Console; import camp.nextstep.edu.missionutils.Randoms; import java.util.ArrayList; @@ -13,7 +9,8 @@ public class Application { public class Application { public static void main(String[] args) { System.out.println("경주할 자동차 이름을 입력하세요.(이름은 쉼표(,) 기준으로 구분)"); - String[] names = Console.readLine().split(","); + String inputNames = Console.readLine(); + String[] names = inputNames.split(","); List cars = createCars(names); System.out.println("시도할 회수는 몇회인가요?"); @@ -39,7 +36,9 @@ private static List createCars(String[] names) { private static int parseTryCount(String input) { try { int count = Integer.parseInt(input); - if (count < 0) throw new IllegalArgumentException(); + if (count < 0) { + throw new IllegalArgumentException("시도 회수는 0 이상이어야 합니다."); + } return count; } catch (NumberFormatException e) { throw new IllegalArgumentException("숫자만 입력 가능합니다."); From 1ad3029bfaebb5ed86267a78cc6604b53957ab39 Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Mon, 30 Mar 2026 23:36:11 +0900 Subject: [PATCH 07/22] =?UTF-8?q?=EC=9E=90=EB=8F=99=EC=B0=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/Car.java | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/src/main/java/racingcar/Car.java b/src/main/java/racingcar/Car.java index e17cdb3..baf8113 100644 --- a/src/main/java/racingcar/Car.java +++ b/src/main/java/racingcar/Car.java @@ -1,11 +1,9 @@ package racingcar; - -public class Application { + { public static void main(String[] args) { // TODO: 프로그램 구현 } } -package racingcar; public class Car { private final String name; From 6f886e6b7e90e65a1d70bd767c6dc13ee0e7bec8 Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Mon, 30 Mar 2026 23:48:43 +0900 Subject: [PATCH 08/22] =?UTF-8?q?=EC=9E=90=EB=8F=99=EC=B0=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/Car.java | 54 ++++++++++++++++---------------- 1 file changed, 27 insertions(+), 27 deletions(-) diff --git a/src/main/java/racingcar/Car.java b/src/main/java/racingcar/Car.java index baf8113..9c7ba6d 100644 --- a/src/main/java/racingcar/Car.java +++ b/src/main/java/racingcar/Car.java @@ -1,41 +1,41 @@ package racingcar; - { + public static void main(String[] args) { // TODO: 프로그램 구현 } -} +package racingcar; -public class Car { - private final String name; - private int position = 0; + public class Car { + private final String name; + private int position = 0; - public Car(String name) { - validateName(name); - this.name = name; - } + public Car(String name) { + validateName(name); + this.name = name; + } - private void validateName(String name) { - if (name == null || name.isBlank() || name.length() > 5) { - throw new IllegalArgumentException("자동차 이름은 1자 이상 5자 이하만 가능합니다."); + private void validateName(String name) { + if (name == null || name.isBlank() || name.length() > 5) { + throw new IllegalArgumentException("자동차 이름은 1자 이상 5자 이하만 가능합니다."); + } } - } - public void move(int number) { - if (number >= 4) { - position++; + public void move(int number) { + if (number >= 4) { + position++; + } } - } - public String getName() { - return name; - } + public String getName() { + return name; + } - public int getPosition() { - return position; - } + public int getPosition() { + return position; + } - // 현재 위치를 "-"로 변환하여 출력 형식 반환 - public String getStatusString() { - return name + " : " + "-".repeat(position); + public String getStatusString() { + return name + " : " + "-".repeat(position); + } } -} + From ae2b83bd029e156d90b9f8adbc8725b3e5f198ff Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 20:54:20 +0900 Subject: [PATCH 09/22] =?UTF-8?q?=EC=9E=90=EB=8F=99=EC=B0=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/model/Car.java | 39 ++++++++++++++++++++++++++ 1 file changed, 39 insertions(+) create mode 100644 src/main/java/racingcar/model/Car.java diff --git a/src/main/java/racingcar/model/Car.java b/src/main/java/racingcar/model/Car.java new file mode 100644 index 0000000..641527c --- /dev/null +++ b/src/main/java/racingcar/model/Car.java @@ -0,0 +1,39 @@ +package racingcar.model; + +public class Car { +} +package racingcar.model; + +public class Car { + private final String name; + private int position = 0; + + public Car(String name) { + validateName(name); + this.name = name; + } + + private void validateName(String name) { + if (name == null || name.isBlank() || name.length() > 5) { + throw new IllegalArgumentException("자동차 이름은 1자 이상 5자 이하만 가능합니다."); + } + } + + public void move(int randomNumber) { + if (randomNumber >= 4) { + position++; + } + } + + public String getName() { + return name; + } + + public int getPosition() { + return position; + } + + public String getPositionVisual() { + return "-".repeat(position); + } +} \ No newline at end of file From c54b0ab52ee44d16efc05e980f1e443b60515037 Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 20:54:50 +0900 Subject: [PATCH 10/22] =?UTF-8?q?=EC=A7=84=ED=96=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/Application.java | 69 ------------------------ 1 file changed, 69 deletions(-) delete mode 100644 src/main/java/racingcar/Application.java diff --git a/src/main/java/racingcar/Application.java b/src/main/java/racingcar/Application.java deleted file mode 100644 index 160a28f..0000000 --- a/src/main/java/racingcar/Application.java +++ /dev/null @@ -1,69 +0,0 @@ -package racingcar; - -import camp.nextstep.edu.missionutils.Console; -import camp.nextstep.edu.missionutils.Randoms; -import java.util.ArrayList; -import java.util.List; -import java.util.StringJoiner; - -public class Application { - public static void main(String[] args) { - System.out.println("경주할 자동차 이름을 입력하세요.(이름은 쉼표(,) 기준으로 구분)"); - String inputNames = Console.readLine(); - String[] names = inputNames.split(","); - List cars = createCars(names); - - System.out.println("시도할 회수는 몇회인가요?"); - int tryCount = parseTryCount(Console.readLine()); - - System.out.println("\n실행 결과"); - for (int i = 0; i < tryCount; i++) { - playOneRound(cars); - System.out.println(); - } - - printFinalWinners(cars); - } - - private static List createCars(String[] names) { - List cars = new ArrayList<>(); - for (String name : names) { - cars.add(new Car(name.trim())); - } - return cars; - } - - private static int parseTryCount(String input) { - try { - int count = Integer.parseInt(input); - if (count < 0) { - throw new IllegalArgumentException("시도 회수는 0 이상이어야 합니다."); - } - return count; - } catch (NumberFormatException e) { - throw new IllegalArgumentException("숫자만 입력 가능합니다."); - } - } - - private static void playOneRound(List cars) { - for (Car car : cars) { - car.move(Randoms.pickNumberInRange(0, 9)); - System.out.println(car.getStatusString()); - } - } - - private static void printFinalWinners(List cars) { - int maxPosition = 0; - for (Car car : cars) { - maxPosition = Math.max(maxPosition, car.getPosition()); - } - - StringJoiner winners = new StringJoiner(", "); - for (Car car : cars) { - if (car.getPosition() == maxPosition) { - winners.add(car.getName()); - } - } - System.out.println("최종 우승자 : " + winners.toString()); - } -} \ No newline at end of file From d6bab985eef0f13bed8f3d443937dd27cb617ae9 Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 20:55:15 +0900 Subject: [PATCH 11/22] =?UTF-8?q?=EC=9E=85=EB=A0=A5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/view/InputView.java | 35 +++++++++++++++++++++ 1 file changed, 35 insertions(+) create mode 100644 src/main/java/racingcar/view/InputView.java diff --git a/src/main/java/racingcar/view/InputView.java b/src/main/java/racingcar/view/InputView.java new file mode 100644 index 0000000..fc329b4 --- /dev/null +++ b/src/main/java/racingcar/view/InputView.java @@ -0,0 +1,35 @@ +package racingcar.view; + +public class InputView { +} +package racingcar.view; + +import camp.nextstep.edu.missionutils.Console; +import java.util.Arrays; +import java.util.List; + +public class InputView { + public List readCarNames() { + System.out.println("경주할 자동차 이름을 입력하세요.(이름은 쉼표(,) 기준으로 구분)"); + String input = Console.readLine(); + return Arrays.asList(input.split(",")); + } + + public int readAttemptCount() { + System.out.println("시도할 회수는 몇회인가요?"); + String input = Console.readLine(); + try { + int count = Integer.parseInt(input); + validateCount(count); + return count; + } catch (NumberFormatException e) { + throw new IllegalArgumentException("시도 횟수는 숫자여야 합니다."); + } + } + + private void validateCount(int count) { + if (count < 1) { + throw new IllegalArgumentException("시도 횟수는 1 이상이어야 합니다."); + } + } +} \ No newline at end of file From 17cfbe923936a3d1f2ba558fc545065bb360a6e2 Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 20:55:21 +0900 Subject: [PATCH 12/22] =?UTF-8?q?=EC=B6=9C=EB=A0=A5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/view/OutputView.java | 25 ++++++++++++++++++++ 1 file changed, 25 insertions(+) create mode 100644 src/main/java/racingcar/view/OutputView.java diff --git a/src/main/java/racingcar/view/OutputView.java b/src/main/java/racingcar/view/OutputView.java new file mode 100644 index 0000000..bc65c36 --- /dev/null +++ b/src/main/java/racingcar/view/OutputView.java @@ -0,0 +1,25 @@ +package racingcar.view; + +public class OutputView { +} +package racingcar.view; + +import racingcar.model.Car; +import java.util.List; + +public class OutputView { + public void printRoundResult(List cars) { + for (Car car : cars) { + System.out.println(car.getName() + " : " + car.getPositionVisual()); + } + System.out.println(); + } + + public void printWinners(List winners) { + System.out.print("최종 우승자 : " + String.join(", ", winners)); + } + + public void printResultHeader() { + System.out.println("\n실행 결과"); + } +} \ No newline at end of file From 35fe5b69cd07a2c2978c63ec308721d57dff12dd Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 20:55:51 +0900 Subject: [PATCH 13/22] =?UTF-8?q?=EA=B2=BD=EC=A3=BC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/model/RacingGame.java | 41 +++++++++++++++++++ 1 file changed, 41 insertions(+) create mode 100644 src/main/java/racingcar/model/RacingGame.java diff --git a/src/main/java/racingcar/model/RacingGame.java b/src/main/java/racingcar/model/RacingGame.java new file mode 100644 index 0000000..662f28e --- /dev/null +++ b/src/main/java/racingcar/model/RacingGame.java @@ -0,0 +1,41 @@ +package racingcar.model; + +public class RacingGame { +} +package racingcar.model; + +import camp.nextstep.edu.missionutils.Randoms; +import java.util.List; +import java.util.stream.Collectors; + +public class RacingGame { + private final List cars; + + public RacingGame(List carNames) { + this.cars = carNames.stream() + .map(Car::new) + .collect(Collectors.toList()); + } + + public void playRound() { + for (Car car : cars) { + car.move(Randoms.pickNumberInRange(0, 9)); + } + } + + public List getCars() { + return cars; + } + + public List getWinners() { + int maxPosition = cars.stream() + .mapToInt(Car::getPosition) + .max() + .orElse(0); + + return cars.stream() + .filter(car -> car.getPosition() == maxPosition) + .map(Car::getName) + .collect(Collectors.toList()); + } +} \ No newline at end of file From 29132397cba9a4c60284501bb533b328a78b540a Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 21:17:05 +0900 Subject: [PATCH 14/22] =?UTF-8?q?=EC=A7=84=ED=96=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/Application.java | 8 ++++++++ 1 file changed, 8 insertions(+) create mode 100644 src/main/java/racingcar/Application.java diff --git a/src/main/java/racingcar/Application.java b/src/main/java/racingcar/Application.java new file mode 100644 index 0000000..66181f2 --- /dev/null +++ b/src/main/java/racingcar/Application.java @@ -0,0 +1,8 @@ +package racingcar; + +public class Application { + public static void main(String[] args) { + RacingGame game = new RacingGame(); + game.run(); + } +} \ No newline at end of file From 6ad7e805de7da241f08f156197b068df005b795b Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 21:17:21 +0900 Subject: [PATCH 15/22] =?UTF-8?q?=EC=9E=90=EB=8F=99=EC=B0=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/Car.java | 50 +++++++++----------------- src/main/java/racingcar/model/Car.java | 39 -------------------- 2 files changed, 16 insertions(+), 73 deletions(-) delete mode 100644 src/main/java/racingcar/model/Car.java diff --git a/src/main/java/racingcar/Car.java b/src/main/java/racingcar/Car.java index 9c7ba6d..0a40eb7 100644 --- a/src/main/java/racingcar/Car.java +++ b/src/main/java/racingcar/Car.java @@ -1,41 +1,23 @@ package racingcar; - public static void main(String[] args) { - // TODO: 프로그램 구현 - } -package racingcar; - - public class Car { - private final String name; - private int position = 0; - - public Car(String name) { - validateName(name); - this.name = name; - } - - private void validateName(String name) { - if (name == null || name.isBlank() || name.length() > 5) { - throw new IllegalArgumentException("자동차 이름은 1자 이상 5자 이하만 가능합니다."); - } - } +public class Car { + private final String name; + private int position; - public void move(int number) { - if (number >= 4) { - position++; - } - } - - public String getName() { - return name; - } + public Car(String name) { + this.name = name; + this.position = 0; + } - public int getPosition() { - return position; - } + public void move() { + position++; + } - public String getStatusString() { - return name + " : " + "-".repeat(position); - } + public String getName() { + return name; } + public int getPosition() { + return position; + } +} \ No newline at end of file diff --git a/src/main/java/racingcar/model/Car.java b/src/main/java/racingcar/model/Car.java deleted file mode 100644 index 641527c..0000000 --- a/src/main/java/racingcar/model/Car.java +++ /dev/null @@ -1,39 +0,0 @@ -package racingcar.model; - -public class Car { -} -package racingcar.model; - -public class Car { - private final String name; - private int position = 0; - - public Car(String name) { - validateName(name); - this.name = name; - } - - private void validateName(String name) { - if (name == null || name.isBlank() || name.length() > 5) { - throw new IllegalArgumentException("자동차 이름은 1자 이상 5자 이하만 가능합니다."); - } - } - - public void move(int randomNumber) { - if (randomNumber >= 4) { - position++; - } - } - - public String getName() { - return name; - } - - public int getPosition() { - return position; - } - - public String getPositionVisual() { - return "-".repeat(position); - } -} \ No newline at end of file From c20713ce44ffeecbe35d9fb209c885fcb1c80643 Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 21:17:29 +0900 Subject: [PATCH 16/22] =?UTF-8?q?=EC=9E=85=EB=A0=A5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/InputHandler.java | 30 ++++++++++++++++++ src/main/java/racingcar/view/InputView.java | 35 --------------------- 2 files changed, 30 insertions(+), 35 deletions(-) create mode 100644 src/main/java/racingcar/InputHandler.java delete mode 100644 src/main/java/racingcar/view/InputView.java diff --git a/src/main/java/racingcar/InputHandler.java b/src/main/java/racingcar/InputHandler.java new file mode 100644 index 0000000..b2f1b81 --- /dev/null +++ b/src/main/java/racingcar/InputHandler.java @@ -0,0 +1,30 @@ +package racingcar; + +import camp.nextstep.edu.missionutils.Console; +import java.util.ArrayList; +import java.util.List; + +public class InputHandler { + + public List readCars() { + System.out.println("경주할 자동차 이름을 입력하세요.(이름은 쉼표(,) 기준으로 구분)"); + String input = Console.readLine(); + String[] names = input.split(",", -1); + return parseCars(names); + } + + private List parseCars(String[] names) { + List cars = new ArrayList<>(); + for (String name : names) { + Validator.validateCarName(name.trim()); + cars.add(new Car(name.trim())); + } + return cars; + } + + public int readAttemptCount() { + System.out.println("시도할 회수는 몇회인가요?"); + String input = Console.readLine(); + return Validator.validateAndParseAttemptCount(input); + } +} \ No newline at end of file diff --git a/src/main/java/racingcar/view/InputView.java b/src/main/java/racingcar/view/InputView.java deleted file mode 100644 index fc329b4..0000000 --- a/src/main/java/racingcar/view/InputView.java +++ /dev/null @@ -1,35 +0,0 @@ -package racingcar.view; - -public class InputView { -} -package racingcar.view; - -import camp.nextstep.edu.missionutils.Console; -import java.util.Arrays; -import java.util.List; - -public class InputView { - public List readCarNames() { - System.out.println("경주할 자동차 이름을 입력하세요.(이름은 쉼표(,) 기준으로 구분)"); - String input = Console.readLine(); - return Arrays.asList(input.split(",")); - } - - public int readAttemptCount() { - System.out.println("시도할 회수는 몇회인가요?"); - String input = Console.readLine(); - try { - int count = Integer.parseInt(input); - validateCount(count); - return count; - } catch (NumberFormatException e) { - throw new IllegalArgumentException("시도 횟수는 숫자여야 합니다."); - } - } - - private void validateCount(int count) { - if (count < 1) { - throw new IllegalArgumentException("시도 횟수는 1 이상이어야 합니다."); - } - } -} \ No newline at end of file From d963609491902f64ac97c2ec7eed6f3b0b80df49 Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 21:17:37 +0900 Subject: [PATCH 17/22] =?UTF-8?q?=EC=B6=9C=EB=A0=A5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/OutputHandler.java | 29 ++++++++++++++++++++ src/main/java/racingcar/view/OutputView.java | 25 ----------------- 2 files changed, 29 insertions(+), 25 deletions(-) create mode 100644 src/main/java/racingcar/OutputHandler.java delete mode 100644 src/main/java/racingcar/view/OutputView.java diff --git a/src/main/java/racingcar/OutputHandler.java b/src/main/java/racingcar/OutputHandler.java new file mode 100644 index 0000000..b26ebd1 --- /dev/null +++ b/src/main/java/racingcar/OutputHandler.java @@ -0,0 +1,29 @@ +package racingcar; + +import java.util.List; +import java.util.stream.Collectors; + +public class OutputHandler { + + public void printRoundResult(List cars) { + for (Car car : cars) { + System.out.println(car.getName() + " : " + buildProgressBar(car.getPosition())); + } + System.out.println(); + } + + private String buildProgressBar(int position) { + StringBuilder sb = new StringBuilder(); + for (int i = 0; i < position; i++) { + sb.append("-"); + } + return sb.toString(); + } + + public void printWinners(List winners) { + String names = winners.stream() + .map(Car::getName) + .collect(Collectors.joining(", ")); + System.out.println("최종 우승자 : " + names); + } +} \ No newline at end of file diff --git a/src/main/java/racingcar/view/OutputView.java b/src/main/java/racingcar/view/OutputView.java deleted file mode 100644 index bc65c36..0000000 --- a/src/main/java/racingcar/view/OutputView.java +++ /dev/null @@ -1,25 +0,0 @@ -package racingcar.view; - -public class OutputView { -} -package racingcar.view; - -import racingcar.model.Car; -import java.util.List; - -public class OutputView { - public void printRoundResult(List cars) { - for (Car car : cars) { - System.out.println(car.getName() + " : " + car.getPositionVisual()); - } - System.out.println(); - } - - public void printWinners(List winners) { - System.out.print("최종 우승자 : " + String.join(", ", winners)); - } - - public void printResultHeader() { - System.out.println("\n실행 결과"); - } -} \ No newline at end of file From fff259c392f1c0a90c0c0f55404280c5e9eb7989 Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 21:17:44 +0900 Subject: [PATCH 18/22] =?UTF-8?q?=EA=B2=BD=EC=A3=BC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/RacingGame.java | 67 +++++++++++++++++++ src/main/java/racingcar/model/RacingGame.java | 41 ------------ 2 files changed, 67 insertions(+), 41 deletions(-) create mode 100644 src/main/java/racingcar/RacingGame.java delete mode 100644 src/main/java/racingcar/model/RacingGame.java diff --git a/src/main/java/racingcar/RacingGame.java b/src/main/java/racingcar/RacingGame.java new file mode 100644 index 0000000..82c8c80 --- /dev/null +++ b/src/main/java/racingcar/RacingGame.java @@ -0,0 +1,67 @@ +package racingcar; + +import camp.nextstep.edu.missionutils.Randoms; +import java.util.List; +import java.util.stream.Collectors; + +public class RacingGame { + + private static final int MOVE_THRESHOLD = 4; + + private final InputHandler inputHandler; + private final OutputHandler outputHandler; + + public RacingGame() { + this.inputHandler = new InputHandler(); + this.outputHandler = new OutputHandler(); + } + + public void run() { + List cars = inputHandler.readCars(); + int attemptCount = inputHandler.readAttemptCount(); + + System.out.println(); + System.out.println("실행 결과"); + + playRounds(cars, attemptCount); + + outputHandler.printWinners(findWinners(cars)); + } + + private void playRounds(List cars, int attemptCount) { + for (int i = 0; i < attemptCount; i++) { + playOneRound(cars); + outputHandler.printRoundResult(cars); + } + } + + private void playOneRound(List cars) { + for (Car car : cars) { + moveIfPossible(car); + } + } + + private void moveIfPossible(Car car) { + if (isMovable()) { + car.move(); + } + } + + private boolean isMovable() { + return Randoms.pickNumberInRange(0, 9) >= MOVE_THRESHOLD; + } + + private List findWinners(List cars) { + int maxPosition = findMaxPosition(cars); + return cars.stream() + .filter(car -> car.getPosition() == maxPosition) + .collect(Collectors.toList()); + } + + private int findMaxPosition(List cars) { + return cars.stream() + .mapToInt(Car::getPosition) + .max() + .orElse(0); + } +} \ No newline at end of file diff --git a/src/main/java/racingcar/model/RacingGame.java b/src/main/java/racingcar/model/RacingGame.java deleted file mode 100644 index 662f28e..0000000 --- a/src/main/java/racingcar/model/RacingGame.java +++ /dev/null @@ -1,41 +0,0 @@ -package racingcar.model; - -public class RacingGame { -} -package racingcar.model; - -import camp.nextstep.edu.missionutils.Randoms; -import java.util.List; -import java.util.stream.Collectors; - -public class RacingGame { - private final List cars; - - public RacingGame(List carNames) { - this.cars = carNames.stream() - .map(Car::new) - .collect(Collectors.toList()); - } - - public void playRound() { - for (Car car : cars) { - car.move(Randoms.pickNumberInRange(0, 9)); - } - } - - public List getCars() { - return cars; - } - - public List getWinners() { - int maxPosition = cars.stream() - .mapToInt(Car::getPosition) - .max() - .orElse(0); - - return cars.stream() - .filter(car -> car.getPosition() == maxPosition) - .map(Car::getName) - .collect(Collectors.toList()); - } -} \ No newline at end of file From d4a6b5a4a72eece6405a6c6a38235adeb53fbf32 Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 21:17:51 +0900 Subject: [PATCH 19/22] =?UTF-8?q?=ED=85=8C=EC=8A=A4=ED=8A=B8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/test/RacingGameTest.java | 59 ++++++++++++++++++++++++++ 1 file changed, 59 insertions(+) create mode 100644 src/main/java/test/RacingGameTest.java diff --git a/src/main/java/test/RacingGameTest.java b/src/main/java/test/RacingGameTest.java new file mode 100644 index 0000000..32d7ea0 --- /dev/null +++ b/src/main/java/test/RacingGameTest.java @@ -0,0 +1,59 @@ +package racingcar; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.Assertions.*; + +class RacingGameTest { + + @Test + @DisplayName("자동차가 이동 후 위치가 1 증가한다") + void carMoveTest() { + Car car = new Car("pobi"); + car.move(); + assertThat(car.getPosition()).isEqualTo(1); + } + + @Test + @DisplayName("이동하지 않으면 위치는 0이다") + void carNoMoveTest() { + Car car = new Car("woni"); + assertThat(car.getPosition()).isEqualTo(0); + } + + @Test + @DisplayName("자동차 이름이 5자를 초과하면 예외가 발생한다") + void invalidCarNameLengthTest() { + assertThatThrownBy(() -> Validator.validateCarName("toolongname")) + .isInstanceOf(IllegalArgumentException.class); + } + + @Test + @DisplayName("자동차 이름이 공백이면 예외가 발생한다") + void blankCarNameTest() { + assertThatThrownBy(() -> Validator.validateCarName(" ")) + .isInstanceOf(IllegalArgumentException.class); + } + + @Test + @DisplayName("시도 횟수가 숫자가 아니면 예외가 발생한다") + void invalidAttemptCountFormatTest() { + assertThatThrownBy(() -> Validator.validateAndParseAttemptCount("abc")) + .isInstanceOf(IllegalArgumentException.class); + } + + @Test + @DisplayName("시도 횟수가 0 이하이면 예외가 발생한다") + void invalidAttemptCountRangeTest() { + assertThatThrownBy(() -> Validator.validateAndParseAttemptCount("0")) + .isInstanceOf(IllegalArgumentException.class); + } + + @Test + @DisplayName("5자 이하의 유효한 이름은 예외가 발생하지 않는다") + void validCarNameTest() { + assertThatCode(() -> Validator.validateCarName("pobi")) + .doesNotThrowAnyException(); + } +} \ No newline at end of file From ed4d059c263667d2d9c37e3c1206904fac0eb5ad Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 21:17:57 +0900 Subject: [PATCH 20/22] =?UTF-8?q?=EA=B8=B0=EB=8A=A5=EC=9A=94=EA=B5=AC?= =?UTF-8?q?=EC=82=AC=ED=95=AD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- docs/README.md | 32 +++++++++++++++++--------------- 1 file changed, 17 insertions(+), 15 deletions(-) diff --git a/docs/README.md b/docs/README.md index 8f261c2..a74bb69 100644 --- a/docs/README.md +++ b/docs/README.md @@ -1,15 +1,17 @@ -# 자동차 경주 게임 기능 목록 - -## 기능요구사항 -- [ ] 자동차 이름을 쉼표(,) 기준으로 구분하여 입력받기 -- [ ] 각 자동차에 이름을 부여하기 (5자 이하 검증) -- [ ] 시도할 횟수 입력받기 -- [ ] 0~9 사이의 무작위 값을 구하여 4 이상일 경우 전진하기 -- [ ] 차수별 실행 결과 출력하기 (이름 : ---) -- [ ] 우승자 판별 및 출력하기 (공동 우승 시 쉼표로 구분) - -## ⚠️ 예외 처리 -- [ ] 자동차 이름이 5자를 초과하는 경우 -- [ ] 자동차 이름이 빈 값인 경우 -- [ ] 시도 횟수가 숫자가 아닌 경우 -- [ ] 시도 횟수가 음수인 경우 \ No newline at end of file +# 입력 기능 +경주할 자동차 이름 입력 받기 (쉼표 구분) +시도할 횟수 입력 받기 +# 유효성 검사 기능 +자동차 이름이 공백인 경우 IllegalArgumentException 발생 +자동차 이름이 5자 초과인 경우 IllegalArgumentException 발생 +시도 횟수가 숫자가 아닌 경우 IllegalArgumentException 발생 +시도 횟수가 0 이하인 경우 IllegalArgumentException 발생 +# 자동차 기능 +자동차 이름과 위치(position) 관리 +0~9 무작위 값이 4 이상이면 전진 +# 게임 진행 기능 +입력한 횟수만큼 라운드 반복 실행 +매 라운드 결과 출력 (이름 + 진행 막대) +# 우승자 계산 및 출력 기능 +최대 위치값을 가진 자동차를 우승자로 선정 +공동 우승자 쉼표로 구분하여 출력 \ No newline at end of file From df37a6d8a0df5d21a1313fe892ef91279dd3e16a Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 21:18:43 +0900 Subject: [PATCH 21/22] =?UTF-8?q?=EA=B2=80=EC=82=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/racingcar/Validator.java | 27 ++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) create mode 100644 src/main/java/racingcar/Validator.java diff --git a/src/main/java/racingcar/Validator.java b/src/main/java/racingcar/Validator.java new file mode 100644 index 0000000..07f6b25 --- /dev/null +++ b/src/main/java/racingcar/Validator.java @@ -0,0 +1,27 @@ +package racingcar; + +public class Validator { + + private static final int MAX_NAME_LENGTH = 5; + + public static void validateCarName(String name) { + if (name.isBlank()) { + throw new IllegalArgumentException("자동차 이름은 공백일 수 없습니다."); + } + if (name.length() > MAX_NAME_LENGTH) { + throw new IllegalArgumentException("자동차 이름은 5자 이하만 가능합니다: " + name); + } + } + + public static int validateAndParseAttemptCount(String input) { + try { + int count = Integer.parseInt(input.trim()); + if (count <= 0) { + throw new IllegalArgumentException("시도 횟수는 1 이상이어야 합니다."); + } + return count; + } catch (NumberFormatException e) { + throw new IllegalArgumentException("시도 횟수는 숫자여야 합니다."); + } + } +} \ No newline at end of file From 02fa6204c270b6acbb3a4d7cd17bc29cefe65b3d Mon Sep 17 00:00:00 2001 From: dlarudtns07-oss Date: Wed, 1 Apr 2026 21:23:12 +0900 Subject: [PATCH 22/22] =?UTF-8?q?=ED=85=8C=EC=8A=A4=ED=8A=B8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/{main/java/test => test/java/racingcar}/RacingGameTest.java | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename src/{main/java/test => test/java/racingcar}/RacingGameTest.java (100%) diff --git a/src/main/java/test/RacingGameTest.java b/src/test/java/racingcar/RacingGameTest.java similarity index 100% rename from src/main/java/test/RacingGameTest.java rename to src/test/java/racingcar/RacingGameTest.java