diff --git a/src/main/java/object b/src/main/java/object new file mode 100644 index 0000000000..8b13789179 --- /dev/null +++ b/src/main/java/object @@ -0,0 +1 @@ + diff --git a/src/main/java/racingcar/Application.java b/src/main/java/racingcar/Application.java index a17a52e724..b012471222 100644 --- a/src/main/java/racingcar/Application.java +++ b/src/main/java/racingcar/Application.java @@ -1,7 +1,156 @@ package racingcar; +import camp.nextstep.edu.missionutils.Console; +import camp.nextstep.edu.missionutils.Randoms; +import object.Car; + +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + public class Application { + + public class Error{ + public static final String EMPTY_INPUT_VALUE_MESSAGE = "값을 필수로 입력해야 합니다."; + public static final String CAR_NAME_LENGTH_MESSAGE = "자동차의 이름은 5글자를 넘길 수 없습니다."; + public static final String INVALID_NUMBER_MESSAGE = "유효한 숫자를 입력해야 합니다."; + } + + public class GameConstants { + public static final int MAX_CAR_NAME_LENGTH = 5; + public static final int MIN_RANDOM_VALUE = 0; + public static final int MAX_RANDOM_VALUE = 9; + public static final int ADVANCE_THRESHOLD = 4; + } + + public class TextFormat { + public static final String CAR_STATUS_FORMAT = "%s : %s"; + public static final String DELIMITER = ","; + } + public static void main(String[] args) { - // TODO: 프로그램 구현 + String carName = carNameInput(); + List carNameList = splitCarNamesByComma(carName); + validateCarNames(carNameList); + + int tryCount = getTryCount(); + List cars = initializeCars(carNameList); + + startRace(cars, tryCount); + printWinners(cars); + } + + private static String carNameInput() { + System.out.println("경주할 자동차 이름을 입력하세요.(이름은 쉼표(,) 기준으로 구분)"); + String carName = Console.readLine(); + + isEmptyInputValue(carName); + + return carName; + } + + private static List splitCarNamesByComma(String carName) { + return Arrays.asList(carName.split(TextFormat.DELIMITER)); + } + + private static void validateCarNames(List carNameList) { + for (String carName : carNameList) { + if (carName.length() > GameConstants.MAX_CAR_NAME_LENGTH) { + throw new IllegalArgumentException(Error.CAR_NAME_LENGTH_MESSAGE); + } + } + } + + private static int getTryCount() { + System.out.println("시도할 횟수는 몇 회인가요?"); + String tryCountInput = Console.readLine(); + + isEmptyInputValue(tryCountInput); + + return parseTryCount(tryCountInput); + } + + private static void isEmptyInputValue(String inputValue) { + if (inputValue == null || inputValue.isEmpty()){ + throw new IllegalArgumentException(Error.EMPTY_INPUT_VALUE_MESSAGE); + } + } + + private static int parseTryCount(String tryCountInput) { + try { + return Integer.parseInt(tryCountInput); + } catch (NumberFormatException e) { + throw new IllegalArgumentException(Error.INVALID_NUMBER_MESSAGE); + } + } + + private static List initializeCars(List carNameList) { + List cars = new ArrayList<>(); + for (String name : carNameList) { + cars.add(new Car(name)); + } + return cars; + } + + private static void startRace(List cars, int tryCount) { + for (int i = 0; i < tryCount; i++) { + raceRound(cars); + System.out.println(); + } + } + + private static void raceRound(List cars) { + for (Car car : cars) { + if (shouldAdvance()) { + car.advance(); + } + System.out.println(String.format(TextFormat.CAR_STATUS_FORMAT, car.getCarName(), "-".repeat(car.getPosition()))); + } + } + + private static boolean shouldAdvance() { + int randomValue = Randoms.pickNumberInRange(GameConstants.MIN_RANDOM_VALUE, GameConstants.MAX_RANDOM_VALUE); + return randomValue >= GameConstants.ADVANCE_THRESHOLD; + } + + private static void printWinners(List cars) { + int maxPosition = getMaxPosition(cars); + List winners = getWinners(cars, maxPosition); + System.out.println("최종 우승자 : " + String.join(TextFormat.DELIMITER + " ", winners)); + } + + private static int getMaxPosition(List cars) { + return cars.stream().mapToInt(Car::getPosition).max().orElse(0); + } + + private static List getWinners(List cars, int maxPosition) { + List winners = new ArrayList<>(); + for (Car car : cars) { + if (car.getPosition() == maxPosition) { + winners.add(car.getCarName()); + } + } + return winners; + } +} + +class Car { + private final String carName; + private int position = 0; + + public Car(String carName) { + this.carName = carName; + } + + public String getCarName() { + return carName; + } + + public int getPosition() { + return position; + } + + public void advance() { + position++; } }