From 4919b568257be1f75207894d7bb3b28fa0db44d1 Mon Sep 17 00:00:00 2001 From: SimJung Date: Sat, 13 May 2023 02:56:52 +0900 Subject: [PATCH 01/14] =?UTF-8?q?=EB=9E=8C=EB=8B=A4=20=EC=8B=A4=EC=8A=B5?= =?UTF-8?q?=201=20-=20=EC=9D=B5=EB=AA=85=20=ED=81=B4=EB=9E=98=EC=8A=A4?= =?UTF-8?q?=EB=A5=BC=20=EB=9E=8C=EB=8B=A4=EB=A1=9C=20=EC=A0=84=ED=99=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/test/java/nextstep/fp/CarTest.java | 14 ++------------ 1 file changed, 2 insertions(+), 12 deletions(-) diff --git a/src/test/java/nextstep/fp/CarTest.java b/src/test/java/nextstep/fp/CarTest.java index 1ab1106fe2..ecab481aec 100644 --- a/src/test/java/nextstep/fp/CarTest.java +++ b/src/test/java/nextstep/fp/CarTest.java @@ -8,24 +8,14 @@ public class CarTest { @Test public void 이동() { Car car = new Car("pobi", 0); - Car actual = car.move(new MoveStrategy() { - @Override - public boolean isMovable() { - return true; - } - }); + Car actual = car.move(() -> true); assertThat(actual).isEqualTo(new Car("pobi", 1)); } @Test public void 정지() { Car car = new Car("pobi", 0); - Car actual = car.move(new MoveStrategy() { - @Override - public boolean isMovable() { - return false; - } - }); + Car actual = car.move(() -> false); assertThat(actual).isEqualTo(new Car("pobi", 0)); } } From 7060fe154ea6dc7ae40e0c5f3d820a05224e6035 Mon Sep 17 00:00:00 2001 From: SimJung Date: Sat, 13 May 2023 03:05:44 +0900 Subject: [PATCH 02/14] =?UTF-8?q?=EB=9E=8C=EB=8B=A4=20=EC=8B=A4=EC=8A=B5?= =?UTF-8?q?=202=20-=20=EB=9E=8C=EB=8B=A4=EB=A5=BC=20=ED=99=9C=EC=9A=A9?= =?UTF-8?q?=ED=95=B4=20=EC=A4=91=EB=B3=B5=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/nextstep/fp/Conditional.java | 5 +++ src/main/java/nextstep/fp/Lambda.java | 38 ++++------------------ src/test/java/nextstep/fp/LambdaTest.java | 6 ++-- 3 files changed, 14 insertions(+), 35 deletions(-) create mode 100644 src/main/java/nextstep/fp/Conditional.java diff --git a/src/main/java/nextstep/fp/Conditional.java b/src/main/java/nextstep/fp/Conditional.java new file mode 100644 index 0000000000..1d48b1b856 --- /dev/null +++ b/src/main/java/nextstep/fp/Conditional.java @@ -0,0 +1,5 @@ +package nextstep.fp; + +public interface Conditional { + boolean test(Integer number); +} diff --git a/src/main/java/nextstep/fp/Lambda.java b/src/main/java/nextstep/fp/Lambda.java index bd68fe1ce6..1e9f0c1126 100644 --- a/src/main/java/nextstep/fp/Lambda.java +++ b/src/main/java/nextstep/fp/Lambda.java @@ -18,39 +18,13 @@ public static void printAllLambda(List numbers) { } public static void runThread() { - new Thread(new Runnable() { - @Override - public void run() { - System.out.println("Hello from thread"); - } - }).start(); + new Thread(() -> System.out.println("Hello from thread")).start(); } - public static int sumAll(List numbers) { - int total = 0; - for (int number : numbers) { - total += number; - } - return total; - } - - public static int sumAllEven(List numbers) { - int total = 0; - for (int number : numbers) { - if (number % 2 == 0) { - total += number; - } - } - return total; - } - - public static int sumAllOverThree(List numbers) { - int total = 0; - for (int number : numbers) { - if (number > 3) { - total += number; - } - } - return total; + public static int sumAll(List numbers, Conditional conditional) { + return numbers.stream() + .filter(conditional::test) + .mapToInt(it -> it) + .sum(); } } diff --git a/src/test/java/nextstep/fp/LambdaTest.java b/src/test/java/nextstep/fp/LambdaTest.java index f240ac6560..0ad1940629 100644 --- a/src/test/java/nextstep/fp/LambdaTest.java +++ b/src/test/java/nextstep/fp/LambdaTest.java @@ -33,19 +33,19 @@ public void runThread() throws Exception { @Test public void sumAll() throws Exception { - int sum = Lambda.sumAll(numbers); + int sum = Lambda.sumAll(numbers, number -> true); assertThat(sum).isEqualTo(21); } @Test public void sumAllEven() throws Exception { - int sum = Lambda.sumAllEven(numbers); + int sum = Lambda.sumAll(numbers, number -> number % 2 == 0); assertThat(sum).isEqualTo(12); } @Test public void sumAllOverThree() throws Exception { - int sum = Lambda.sumAllOverThree(numbers); + int sum = Lambda.sumAll(numbers, number -> number > 3); assertThat(sum).isEqualTo(15); } } From c7a9148ac2efa65b0387a03d6b4e062c395a8968 Mon Sep 17 00:00:00 2001 From: SimJung Date: Sat, 13 May 2023 03:09:36 +0900 Subject: [PATCH 03/14] =?UTF-8?q?map,=20reduce,=20filter=20=EC=8B=A4?= =?UTF-8?q?=EC=8A=B5=201=20-=20sumOverThreeAndDouble=20=ED=85=8C=EC=8A=A4?= =?UTF-8?q?=ED=8A=B8=20pass?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/nextstep/fp/StreamStudy.java | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/main/java/nextstep/fp/StreamStudy.java b/src/main/java/nextstep/fp/StreamStudy.java index b446983a02..f897592942 100644 --- a/src/main/java/nextstep/fp/StreamStudy.java +++ b/src/main/java/nextstep/fp/StreamStudy.java @@ -39,6 +39,9 @@ public static long sumAll(List numbers) { } public static long sumOverThreeAndDouble(List numbers) { - return 0; + return numbers.stream() + .filter(number -> number > 3) + .map(number -> number * 2) + .reduce(0, Integer::sum); } } \ No newline at end of file From c9f160562da35e02bd52d27dbe6341c60b759a63 Mon Sep 17 00:00:00 2001 From: SimJung Date: Sat, 13 May 2023 03:19:48 +0900 Subject: [PATCH 04/14] =?UTF-8?q?map,=20reduce,=20filter=20=EC=8B=A4?= =?UTF-8?q?=EC=8A=B5=202=20-=20printLongestWordTop100()=20=EB=A9=94?= =?UTF-8?q?=EC=84=9C=EB=93=9C=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/nextstep/fp/StreamStudy.java | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/src/main/java/nextstep/fp/StreamStudy.java b/src/main/java/nextstep/fp/StreamStudy.java index f897592942..c41708b2d7 100644 --- a/src/main/java/nextstep/fp/StreamStudy.java +++ b/src/main/java/nextstep/fp/StreamStudy.java @@ -5,6 +5,7 @@ import java.nio.file.Files; import java.nio.file.Paths; import java.util.Arrays; +import java.util.Comparator; import java.util.List; import java.util.stream.Collectors; @@ -27,7 +28,12 @@ public static void printLongestWordTop100() throws IOException { .get("src/main/resources/fp/war-and-peace.txt")), StandardCharsets.UTF_8); List words = Arrays.asList(contents.split("[\\P{L}]+")); - // TODO 이 부분에 구현한다. + words.stream() + .filter(word -> word.length() > 12) + .sorted(Comparator.comparingInt(String::length).reversed()) + .distinct() + .limit(100) + .forEach(word -> System.out.println(word.toLowerCase())); } public static List doubleNumbers(List numbers) { From 51532c099f370ef8d5c06d7cd675724e5e00dbe8 Mon Sep 17 00:00:00 2001 From: SimJung Date: Sat, 13 May 2023 03:25:29 +0900 Subject: [PATCH 05/14] =?UTF-8?q?=EC=9A=94=EA=B5=AC=EC=82=AC=ED=95=AD=201?= =?UTF-8?q?=20-=20Optional=EC=9D=84=20=ED=99=9C=EC=9A=A9=ED=95=B4=20?= =?UTF-8?q?=EC=A1=B0=EA=B1=B4=EC=97=90=20=EB=94=B0=EB=A5=B8=20=EB=B0=98?= =?UTF-8?q?=ED=99=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/nextstep/optional/User.java | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/main/java/nextstep/optional/User.java b/src/main/java/nextstep/optional/User.java index 9614c2f43f..b88cdac03a 100644 --- a/src/main/java/nextstep/optional/User.java +++ b/src/main/java/nextstep/optional/User.java @@ -1,5 +1,7 @@ package nextstep.optional; +import java.util.Optional; + public class User { private String name; private Integer age; @@ -33,7 +35,10 @@ public static boolean ageIsInRange1(User user) { } public static boolean ageIsInRange2(User user) { - return false; + Optional optionalUser = Optional.ofNullable(user); + return optionalUser.map(it -> it.age) + .filter(it -> it >= 30 && it <= 45) + .isPresent(); } @Override From 79be2edf3b6ccfa77675cd250b38698e1bb198c1 Mon Sep 17 00:00:00 2001 From: SimJung Date: Sat, 13 May 2023 03:35:50 +0900 Subject: [PATCH 06/14] =?UTF-8?q?=EC=9A=94=EA=B5=AC=EC=82=AC=ED=95=AD=202?= =?UTF-8?q?=20-=20Optional=EC=97=90=EC=84=9C=20=EA=B0=92=EC=9D=84=20?= =?UTF-8?q?=EB=B0=98=ED=99=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/nextstep/optional/Users.java | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/src/main/java/nextstep/optional/Users.java b/src/main/java/nextstep/optional/Users.java index 6293040de8..63815d1c28 100644 --- a/src/main/java/nextstep/optional/Users.java +++ b/src/main/java/nextstep/optional/Users.java @@ -13,11 +13,9 @@ public class Users { new User("honux", 45)); User getUser(String name) { - for (User user : users) { - if (user.matchName(name)) { - return user; - } - } - return DEFAULT_USER; + return users.stream() + .filter(user -> user.matchName(name)) + .findFirst() + .orElse(DEFAULT_USER); } } From 67146b7b3468b5a791842c09f36d0eeb2d492edc Mon Sep 17 00:00:00 2001 From: SimJung Date: Sat, 13 May 2023 03:38:42 +0900 Subject: [PATCH 07/14] =?UTF-8?q?=EC=9A=94=EA=B5=AC=EC=82=AC=ED=95=AD=203?= =?UTF-8?q?=20-=20Optional=EC=97=90=EC=84=9C=20exception=20=EC=B2=98?= =?UTF-8?q?=EB=A6=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/nextstep/optional/Expression.java | 15 +++++++-------- 1 file changed, 7 insertions(+), 8 deletions(-) diff --git a/src/main/java/nextstep/optional/Expression.java b/src/main/java/nextstep/optional/Expression.java index 1c98cd6a62..969e4d5b04 100644 --- a/src/main/java/nextstep/optional/Expression.java +++ b/src/main/java/nextstep/optional/Expression.java @@ -1,9 +1,11 @@ package nextstep.optional; +import java.util.Arrays; + enum Expression { PLUS("+"), MINUS("-"), TIMES("*"), DIVIDE("/"); - private String expression; + private final String expression; Expression(String expression) { this.expression = expression; @@ -14,12 +16,9 @@ private static boolean matchExpression(Expression e, String expression) { } static Expression of(String expression) { - for (Expression v : values()) { - if (matchExpression(v, expression)) { - return v; - } - } - - throw new IllegalArgumentException(String.format("%s는 사칙연산에 해당하지 않는 표현식입니다.", expression)); + return Arrays.stream(values()) + .filter(it -> matchExpression(it, expression)) + .findFirst() + .orElseThrow(() -> new IllegalArgumentException(String.format("%s는 사칙연산에 해당하지 않는 표현식입니다.", expression))); } } From ef3f71c402863fec6716e03671e17484e94fd851 Mon Sep 17 00:00:00 2001 From: SimJung Date: Mon, 15 May 2023 00:09:19 +0900 Subject: [PATCH 08/14] =?UTF-8?q?feat=20:=20Conditional=EC=9D=84=20Predica?= =?UTF-8?q?te=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/nextstep/fp/Conditional.java | 5 ----- src/main/java/nextstep/fp/Lambda.java | 4 ++-- 2 files changed, 2 insertions(+), 7 deletions(-) delete mode 100644 src/main/java/nextstep/fp/Conditional.java diff --git a/src/main/java/nextstep/fp/Conditional.java b/src/main/java/nextstep/fp/Conditional.java deleted file mode 100644 index 1d48b1b856..0000000000 --- a/src/main/java/nextstep/fp/Conditional.java +++ /dev/null @@ -1,5 +0,0 @@ -package nextstep.fp; - -public interface Conditional { - boolean test(Integer number); -} diff --git a/src/main/java/nextstep/fp/Lambda.java b/src/main/java/nextstep/fp/Lambda.java index 66e752a24d..ebb937e3af 100644 --- a/src/main/java/nextstep/fp/Lambda.java +++ b/src/main/java/nextstep/fp/Lambda.java @@ -23,9 +23,9 @@ public static void runThread() { new Thread(() -> System.out.println("Hello from thread")).start(); } - public static int sumAll(List numbers, Conditional conditional) { + public static int sumAll(List numbers, Predicate predicate) { return numbers.stream() - .filter(conditional::test) + .filter(predicate) .mapToInt(it -> it) .sum(); } From d1728d474f0110effe75fe2c39b5648fd08ed5cf Mon Sep 17 00:00:00 2001 From: SimJung Date: Mon, 15 May 2023 00:13:22 +0900 Subject: [PATCH 09/14] =?UTF-8?q?refactor=20:=20matchExpression=20static?= =?UTF-8?q?=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/nextstep/optional/Expression.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/java/nextstep/optional/Expression.java b/src/main/java/nextstep/optional/Expression.java index 969e4d5b04..e87d58001a 100644 --- a/src/main/java/nextstep/optional/Expression.java +++ b/src/main/java/nextstep/optional/Expression.java @@ -11,13 +11,13 @@ enum Expression { this.expression = expression; } - private static boolean matchExpression(Expression e, String expression) { - return expression.equals(e.expression); + private boolean matchExpression(String expression) { + return expression.equals(this.expression); } static Expression of(String expression) { return Arrays.stream(values()) - .filter(it -> matchExpression(it, expression)) + .filter(it -> it.matchExpression(expression)) .findFirst() .orElseThrow(() -> new IllegalArgumentException(String.format("%s는 사칙연산에 해당하지 않는 표현식입니다.", expression))); } From 51703471e27d7a446e918fce6354b011eccdc13e Mon Sep 17 00:00:00 2001 From: SimJung Date: Mon, 15 May 2023 00:16:18 +0900 Subject: [PATCH 10/14] =?UTF-8?q?fix=20:=20age=EC=9D=98=20null=20=EC=B2=B4?= =?UTF-8?q?=ED=81=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/nextstep/optional/User.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/nextstep/optional/User.java b/src/main/java/nextstep/optional/User.java index 5fac8a2821..b898f07c05 100644 --- a/src/main/java/nextstep/optional/User.java +++ b/src/main/java/nextstep/optional/User.java @@ -36,8 +36,8 @@ public static boolean ageIsInRange1(User user) { public static boolean ageIsInRange2(User user) { return Optional.ofNullable(user) - .map(it -> it.age) - .filter(it -> it >= 30 && it <= 45) + .filter(it -> it.age != null) + .filter(it -> it.age >= 30 && it.age <= 45) .isPresent(); } From 226645deb3c8a2c306a97f66ef746463bf783b21 Mon Sep 17 00:00:00 2001 From: SimJung Date: Mon, 15 May 2023 00:25:17 +0900 Subject: [PATCH 11/14] =?UTF-8?q?docs=20:=20README.md=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/ladder/README.md | 12 ++++++++++++ 1 file changed, 12 insertions(+) create mode 100644 src/main/java/ladder/README.md diff --git a/src/main/java/ladder/README.md b/src/main/java/ladder/README.md new file mode 100644 index 0000000000..148f3e4dfd --- /dev/null +++ b/src/main/java/ladder/README.md @@ -0,0 +1,12 @@ +# 🚀2단계 - 사다리(생성) + +## 기능 요구사항 +- 사다리 게임에 참여하는 사람에 이름을 최대5글자까지 부여할 수 있다. 사다리를 출력할 때 사람 이름도 같이 출력한다. +- 사람 이름은 쉼표(,)를 기준으로 구분한다. +- 사람 이름을 5자 기준으로 출력하기 때문에 사다리 폭도 넓어져야 한다. +- 사다리 타기가 정상적으로 동작하려면 라인이 겹치지 않도록 해야 한다. +- |-----|-----| 모양과 같이 가로 라인이 겹치는 경우 어느 방향으로 이동할지 결정할 수 없다. + +## 프로그래밍 요구사항 +- 자바 8의 스트림과 람다를 적용해 프로그래밍한다. +- 규칙 6: 모든 엔티티를 작게 유지한다. \ No newline at end of file From 20e0660cb59df6d0b90cf71c1a3eb5e38cb531be Mon Sep 17 00:00:00 2001 From: SimJung Date: Mon, 15 May 2023 00:47:06 +0900 Subject: [PATCH 12/14] =?UTF-8?q?feat=20:=20=EC=82=AC=EB=8B=A4=EB=A6=AC=20?= =?UTF-8?q?=EA=B2=8C=EC=9E=84=EC=97=90=20=EC=B0=B8=EC=97=AC=ED=95=98?= =?UTF-8?q?=EB=8A=94=20=EC=82=AC=EB=9E=8C=EC=97=90=20=EC=9D=B4=EB=A6=84?= =?UTF-8?q?=EC=9D=84=20=EC=B5=9C=EB=8C=80=205=EA=B8=80=EC=9E=90=20?= =?UTF-8?q?=EA=B9=8C=EC=A7=80=20=EB=B6=80=EC=97=AC=ED=95=A0=20=EC=88=98=20?= =?UTF-8?q?=EC=9E=88=EB=8B=A4.=20=20-=20=EC=82=AC=EB=9E=8C=20=EC=9D=B4?= =?UTF-8?q?=EB=A6=84=EC=9D=80=20=EC=89=BC=ED=91=9C=EB=A5=BC=20=EA=B8=B0?= =?UTF-8?q?=EC=A4=80=EC=9C=BC=EB=A1=9C=20=EA=B5=AC=EB=B6=84=ED=95=9C?= =?UTF-8?q?=EB=8B=A4.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/ladder/domain/Player.java | 21 +++++++++++++++++++ src/main/java/ladder/domain/Players.java | 19 +++++++++++++++++ .../java/ladder/domain/PlayersGenerator.java | 19 +++++++++++++++++ .../exception/IllegalPlayerNameException.java | 9 ++++++++ src/test/java/ladder/domain/PlayerTest.java | 18 ++++++++++++++++ .../ladder/domain/PlayersGeneratorTest.java | 18 ++++++++++++++++ src/test/java/ladder/domain/PlayersTest.java | 21 +++++++++++++++++++ 7 files changed, 125 insertions(+) create mode 100644 src/main/java/ladder/domain/Player.java create mode 100644 src/main/java/ladder/domain/Players.java create mode 100644 src/main/java/ladder/domain/PlayersGenerator.java create mode 100644 src/main/java/ladder/exception/IllegalPlayerNameException.java create mode 100644 src/test/java/ladder/domain/PlayerTest.java create mode 100644 src/test/java/ladder/domain/PlayersGeneratorTest.java create mode 100644 src/test/java/ladder/domain/PlayersTest.java diff --git a/src/main/java/ladder/domain/Player.java b/src/main/java/ladder/domain/Player.java new file mode 100644 index 0000000000..1358c5ba44 --- /dev/null +++ b/src/main/java/ladder/domain/Player.java @@ -0,0 +1,21 @@ +package ladder.domain; + +import ladder.exception.IllegalPlayerNameException; + +public class Player { + private static final int MAX_PLAYER_NAME_LENGTH = 5; + + private final String name; + + public Player(String name) { + if (name.length() > MAX_PLAYER_NAME_LENGTH) { + throw new IllegalPlayerNameException(String.format("입력한 이름 : %s", name)); + } + + this.name = name; + } + + public String getName() { + return name; + } +} diff --git a/src/main/java/ladder/domain/Players.java b/src/main/java/ladder/domain/Players.java new file mode 100644 index 0000000000..b75965b95e --- /dev/null +++ b/src/main/java/ladder/domain/Players.java @@ -0,0 +1,19 @@ +package ladder.domain; + +import java.util.List; + +public class Players { + private final List playerList; + + public Players(List playerList) { + this.playerList = playerList; + } + + public List getPlayerList() { + return List.copyOf(playerList); + } + + public int getPlayerNumber() { + return playerList.size(); + } +} diff --git a/src/main/java/ladder/domain/PlayersGenerator.java b/src/main/java/ladder/domain/PlayersGenerator.java new file mode 100644 index 0000000000..218c6259cd --- /dev/null +++ b/src/main/java/ladder/domain/PlayersGenerator.java @@ -0,0 +1,19 @@ +package ladder.domain; + +import java.util.Arrays; +import java.util.List; +import java.util.stream.Collectors; + +public class PlayersGenerator { + private static final String DEFAULT_SEPARATOR = ","; + private PlayersGenerator() { + } + + public static Players create(String playerNames) { + List playerList = Arrays.stream(playerNames.split(DEFAULT_SEPARATOR)) + .map(Player::new) + .collect(Collectors.toList()); + + return new Players(playerList); + } +} diff --git a/src/main/java/ladder/exception/IllegalPlayerNameException.java b/src/main/java/ladder/exception/IllegalPlayerNameException.java new file mode 100644 index 0000000000..368f5fb088 --- /dev/null +++ b/src/main/java/ladder/exception/IllegalPlayerNameException.java @@ -0,0 +1,9 @@ +package ladder.exception; + +public class IllegalPlayerNameException extends RuntimeException { + private static final String DEFAULT_MESSAGE = "플레이어 이름은 5자를 초과할 수 없습니다."; + + public IllegalPlayerNameException(String message) { + super(String.format("%s %s", DEFAULT_MESSAGE, message)); + } +} diff --git a/src/test/java/ladder/domain/PlayerTest.java b/src/test/java/ladder/domain/PlayerTest.java new file mode 100644 index 0000000000..a3b43cead1 --- /dev/null +++ b/src/test/java/ladder/domain/PlayerTest.java @@ -0,0 +1,18 @@ +package ladder.domain; + +import ladder.exception.IllegalPlayerNameException; +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.AssertionsForClassTypes.*; + +public class PlayerTest { + @Test + void 주어진_문자열로_플레이어_이름을_지정하여_플레이어를_생성할_수_있다() { + assertThat(new Player("abc").getName()).isEqualTo("abc"); + } + + @Test + void 플레이어_이름이_5자를_넘어갈_경우_예외가_발생한다() { + assertThatThrownBy(() -> new Player("abcdef")).isInstanceOf(IllegalPlayerNameException.class); + } +} diff --git a/src/test/java/ladder/domain/PlayersGeneratorTest.java b/src/test/java/ladder/domain/PlayersGeneratorTest.java new file mode 100644 index 0000000000..9de7dd69fe --- /dev/null +++ b/src/test/java/ladder/domain/PlayersGeneratorTest.java @@ -0,0 +1,18 @@ +package ladder.domain; + +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.AssertionsForClassTypes.assertThat; + +public class PlayersGeneratorTest { + @Test + void 쉼표로_구분된_문자열로_플레이어들을_만들_수_있다() { + String playerNames = "pobi,honux,crong,jk"; + Players players = PlayersGenerator.create(playerNames); + assertThat(players.getPlayerList() + .stream() + .map(Player::getName) + .toArray() + ).containsExactly("pobi", "honux", "crong", "jk"); + } +} diff --git a/src/test/java/ladder/domain/PlayersTest.java b/src/test/java/ladder/domain/PlayersTest.java new file mode 100644 index 0000000000..72bff73ee3 --- /dev/null +++ b/src/test/java/ladder/domain/PlayersTest.java @@ -0,0 +1,21 @@ +package ladder.domain; + +import org.junit.jupiter.api.Test; + +import java.util.List; + +import static org.assertj.core.api.AssertionsForClassTypes.assertThat; + +public class PlayersTest { + @Test + void 여러_플레이어들로_Players를_생성하고_Player_리스트를_반환할_수_있다() { + List playerList = List.of(new Player("a"), new Player("b")); + assertThat(new Players(playerList).getPlayerList().containsAll(playerList)).isTrue(); + } + + @Test + void 플레이어가_몇_명인지_알_수_있다() { + List playerList = List.of(new Player("a"), new Player("b")); + assertThat(new Players(playerList).getPlayerNumber()).isEqualTo(2); + } +} From 3bd6f44032eedd07144b07782d6fc435c908b413 Mon Sep 17 00:00:00 2001 From: SimJung Date: Wed, 17 May 2023 18:06:31 +0900 Subject: [PATCH 13/14] =?UTF-8?q?feat=20:=20Ladder=20=EA=B4=80=EB=A0=A8=20?= =?UTF-8?q?=EB=A1=9C=EC=A7=81=20=EA=B5=AC=ED=98=84=20-=20VerticalLine=20?= =?UTF-8?q?=EB=B0=8F=20=EC=BB=AC=EB=A0=89=EC=85=98=20=ED=81=B4=EB=9E=98?= =?UTF-8?q?=EC=8A=A4=20=EC=B6=94=EA=B0=80=20-=20HorizontalLine=20=EB=B0=8F?= =?UTF-8?q?=20=EC=BB=AC=EB=A0=89=EC=85=98=20=ED=81=B4=EB=9E=98=EC=8A=A4=20?= =?UTF-8?q?=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/ladder/README.md | 2 + .../ladder/domain/AdjacentVerticalLines.java | 43 +++++++++++ .../java/ladder/domain/HorizontalLine.java | 32 ++++++++ .../java/ladder/domain/HorizontalLines.java | 40 ++++++++++ src/main/java/ladder/domain/Ladder.java | 66 ++++++++++++++++ src/main/java/ladder/domain/VerticalLine.java | 13 ++++ .../java/ladder/domain/VerticalLines.java | 44 +++++++++++ .../ladder/domain/{ => player}/Player.java | 2 +- .../ladder/domain/{ => player}/Players.java | 2 +- .../domain/{ => player}/PlayersGenerator.java | 3 +- .../ContinuousHorizontalLineException.java | 9 +++ ...IllegalAdjacentVerticalLinesException.java | 9 +++ .../IllegalHorizontalLineHeightException.java | 9 +++ .../IllegalVerticalLineWidthException.java | 9 +++ .../NotEnoughVerticalLinesException.java | 9 +++ .../domain/AdjacentVerticalLinesTest.java | 35 +++++++++ .../ladder/domain/HorizontalLineTest.java | 44 +++++++++++ .../ladder/domain/HorizontalLinesTest.java | 52 +++++++++++++ src/test/java/ladder/domain/LadderTest.java | 75 +++++++++++++++++++ .../java/ladder/domain/VerticalLineTest.java | 12 +++ .../java/ladder/domain/VerticalLinesTest.java | 48 ++++++++++++ .../domain/{ => player}/PlayerTest.java | 5 +- .../{ => player}/PlayersGeneratorTest.java | 2 +- .../domain/{ => player}/PlayersTest.java | 2 +- 24 files changed, 560 insertions(+), 7 deletions(-) create mode 100644 src/main/java/ladder/domain/AdjacentVerticalLines.java create mode 100644 src/main/java/ladder/domain/HorizontalLine.java create mode 100644 src/main/java/ladder/domain/HorizontalLines.java create mode 100644 src/main/java/ladder/domain/Ladder.java create mode 100644 src/main/java/ladder/domain/VerticalLine.java create mode 100644 src/main/java/ladder/domain/VerticalLines.java rename src/main/java/ladder/domain/{ => player}/Player.java (93%) rename src/main/java/ladder/domain/{ => player}/Players.java (92%) rename src/main/java/ladder/domain/{ => player}/PlayersGenerator.java (94%) create mode 100644 src/main/java/ladder/exception/ContinuousHorizontalLineException.java create mode 100644 src/main/java/ladder/exception/IllegalAdjacentVerticalLinesException.java create mode 100644 src/main/java/ladder/exception/IllegalHorizontalLineHeightException.java create mode 100644 src/main/java/ladder/exception/IllegalVerticalLineWidthException.java create mode 100644 src/main/java/ladder/exception/NotEnoughVerticalLinesException.java create mode 100644 src/test/java/ladder/domain/AdjacentVerticalLinesTest.java create mode 100644 src/test/java/ladder/domain/HorizontalLineTest.java create mode 100644 src/test/java/ladder/domain/HorizontalLinesTest.java create mode 100644 src/test/java/ladder/domain/LadderTest.java create mode 100644 src/test/java/ladder/domain/VerticalLineTest.java create mode 100644 src/test/java/ladder/domain/VerticalLinesTest.java rename src/test/java/ladder/domain/{ => player}/PlayerTest.java (74%) rename src/test/java/ladder/domain/{ => player}/PlayersGeneratorTest.java (94%) rename src/test/java/ladder/domain/{ => player}/PlayersTest.java (95%) diff --git a/src/main/java/ladder/README.md b/src/main/java/ladder/README.md index 148f3e4dfd..1d69597365 100644 --- a/src/main/java/ladder/README.md +++ b/src/main/java/ladder/README.md @@ -1,6 +1,7 @@ # 🚀2단계 - 사다리(생성) ## 기능 요구사항 + - 사다리 게임에 참여하는 사람에 이름을 최대5글자까지 부여할 수 있다. 사다리를 출력할 때 사람 이름도 같이 출력한다. - 사람 이름은 쉼표(,)를 기준으로 구분한다. - 사람 이름을 5자 기준으로 출력하기 때문에 사다리 폭도 넓어져야 한다. @@ -8,5 +9,6 @@ - |-----|-----| 모양과 같이 가로 라인이 겹치는 경우 어느 방향으로 이동할지 결정할 수 없다. ## 프로그래밍 요구사항 + - 자바 8의 스트림과 람다를 적용해 프로그래밍한다. - 규칙 6: 모든 엔티티를 작게 유지한다. \ No newline at end of file diff --git a/src/main/java/ladder/domain/AdjacentVerticalLines.java b/src/main/java/ladder/domain/AdjacentVerticalLines.java new file mode 100644 index 0000000000..8cd56194b5 --- /dev/null +++ b/src/main/java/ladder/domain/AdjacentVerticalLines.java @@ -0,0 +1,43 @@ +package ladder.domain; + +import ladder.exception.IllegalAdjacentVerticalLinesException; + +public class AdjacentVerticalLines { + private final VerticalLine leftVerticalLine; + private final VerticalLine rightVerticalLine; + + public AdjacentVerticalLines(VerticalLine firstVerticalLine, VerticalLine secondVerticalLine) { + checkAdjacentVerticalLines(firstVerticalLine, secondVerticalLine); + + this.leftVerticalLine = min(firstVerticalLine, secondVerticalLine); + this.rightVerticalLine = max(firstVerticalLine, secondVerticalLine); + } + + public VerticalLine getLeftVerticalLine() { + return leftVerticalLine; + } + + public VerticalLine getRightVerticalLine() { + return rightVerticalLine; + } + + private void checkAdjacentVerticalLines(VerticalLine firstVerticalLine, VerticalLine secondVerticalLine) { + if (Math.abs(firstVerticalLine.getIndex() - secondVerticalLine.getIndex()) > 1) { + throw new IllegalAdjacentVerticalLinesException( + String.format("입력된 인덱스 : %d, %d", firstVerticalLine.getIndex(), secondVerticalLine.getIndex()) + ); + } + } + + private VerticalLine max(VerticalLine firstVerticalLine, VerticalLine secondVerticalLine) { + return firstVerticalLine.getIndex() > secondVerticalLine.getIndex() + ? firstVerticalLine + : secondVerticalLine; + } + + private VerticalLine min(VerticalLine firstVerticalLine, VerticalLine secondVerticalLine) { + return firstVerticalLine.getIndex() > secondVerticalLine.getIndex() + ? secondVerticalLine + : firstVerticalLine; + } +} diff --git a/src/main/java/ladder/domain/HorizontalLine.java b/src/main/java/ladder/domain/HorizontalLine.java new file mode 100644 index 0000000000..135b38510c --- /dev/null +++ b/src/main/java/ladder/domain/HorizontalLine.java @@ -0,0 +1,32 @@ +package ladder.domain; + +public class HorizontalLine { + private final AdjacentVerticalLines adjacentVerticalLines; + private final int height; + + public HorizontalLine(AdjacentVerticalLines adjacentVerticalLines, int height) { + this.adjacentVerticalLines = adjacentVerticalLines; + this.height = height; + } + + public AdjacentVerticalLines getAdjacentVerticalLines() { + return adjacentVerticalLines; + } + + public int getHeight() { + return height; + } + + public VerticalLine getLeftVerticalLine() { + return adjacentVerticalLines.getLeftVerticalLine(); + } + + public VerticalLine getRightVerticalLine() { + return adjacentVerticalLines.getRightVerticalLine(); + } + + public boolean isConnected(VerticalLine verticalLine) { + return verticalLine == adjacentVerticalLines.getLeftVerticalLine() + || verticalLine == adjacentVerticalLines.getRightVerticalLine(); + } +} diff --git a/src/main/java/ladder/domain/HorizontalLines.java b/src/main/java/ladder/domain/HorizontalLines.java new file mode 100644 index 0000000000..745bc3abe2 --- /dev/null +++ b/src/main/java/ladder/domain/HorizontalLines.java @@ -0,0 +1,40 @@ +package ladder.domain; + +import ladder.exception.IllegalHorizontalLineHeightException; + +import java.util.Set; +import java.util.stream.Collectors; + +public class HorizontalLines { + private final Set horizontalLineSet; + private final int maxHeight; + + public HorizontalLines(Set horizontalLineSet, int maxHeight) { + checkValidHorizontalLineHeight(horizontalLineSet, maxHeight); + + this.horizontalLineSet = horizontalLineSet; + this.maxHeight = maxHeight; + } + + private void checkValidHorizontalLineHeight(Set horizontalLineSet, int maxHeight) { + if (horizontalLineSet.stream() + .anyMatch(it -> it.getHeight() >= maxHeight) + ) { + throw new IllegalHorizontalLineHeightException(String.format("최대 높이 : %d", maxHeight)); + } + } + + public Set getHorizontalLineSet() { + return horizontalLineSet; + } + + public Set getHorizontalLineSetByHeight(int height) { + return horizontalLineSet.stream() + .filter(it -> it.getHeight() == height) + .collect(Collectors.toSet()); + } + + public int getMaxHeight() { + return maxHeight; + } +} diff --git a/src/main/java/ladder/domain/Ladder.java b/src/main/java/ladder/domain/Ladder.java new file mode 100644 index 0000000000..a6998ff783 --- /dev/null +++ b/src/main/java/ladder/domain/Ladder.java @@ -0,0 +1,66 @@ +package ladder.domain; + +import ladder.exception.ContinuousHorizontalLineException; +import ladder.exception.NotEnoughVerticalLinesException; + +import java.util.Set; + +public class Ladder { + private static final int MINIMUM_VERTICAL_LINES_QUANTITY = 2; + + private final VerticalLines verticalLines; + private final HorizontalLines horizontalLines; + + public Ladder(VerticalLines verticalLines, HorizontalLines horizontalLines) { + checkVerticalLines(verticalLines); + checkValidLines(verticalLines, horizontalLines); + + this.verticalLines = verticalLines; + this.horizontalLines = horizontalLines; + } + + private void checkVerticalLines(VerticalLines verticalLines) { + if (verticalLines.getSize() < MINIMUM_VERTICAL_LINES_QUANTITY) { + throw new NotEnoughVerticalLinesException(String.format("세로선 갯수 : %d", verticalLines.getSize())); + } + } + + private void checkValidLines(VerticalLines verticalLines, HorizontalLines horizontalLines) { + for (int i = 0; i < horizontalLines.getMaxHeight(); i++) { + Set horizontalLineSet = horizontalLines.getHorizontalLineSetByHeight(i); + checkExistContinuousHorizontalLinesOnSameHeight(verticalLines, horizontalLineSet); + } + } + + private void checkExistContinuousHorizontalLinesOnSameHeight(VerticalLines verticalLines, Set horizontalLineSet) { + verticalLines.getVerticalLineSet() + .forEach(verticalLine -> + checkConnectingWithManyHorizontalLines(verticalLine, horizontalLineSet) + ); + } + + private void checkConnectingWithManyHorizontalLines(VerticalLine verticalLine, Set horizontalLineSet) { + if (horizontalLineSet.stream() + .filter(it -> it.isConnected(verticalLine)) + .count() > 1 + ) { + throw new ContinuousHorizontalLineException(String.format("중복되는 세로선 위치 : %d", verticalLine.getIndex())); + } + } + + public int getHeight() { + return horizontalLines.getMaxHeight(); + } + + public int getWidth() { + return verticalLines.getMaxWidth(); + } + + public VerticalLines getVerticalLines() { + return verticalLines; + } + + public HorizontalLines getHorizontalLines() { + return horizontalLines; + } +} diff --git a/src/main/java/ladder/domain/VerticalLine.java b/src/main/java/ladder/domain/VerticalLine.java new file mode 100644 index 0000000000..f40c18b99f --- /dev/null +++ b/src/main/java/ladder/domain/VerticalLine.java @@ -0,0 +1,13 @@ +package ladder.domain; + +public class VerticalLine { + private final int index; + + public VerticalLine(int index) { + this.index = index; + } + + public int getIndex() { + return index; + } +} diff --git a/src/main/java/ladder/domain/VerticalLines.java b/src/main/java/ladder/domain/VerticalLines.java new file mode 100644 index 0000000000..c616c153c4 --- /dev/null +++ b/src/main/java/ladder/domain/VerticalLines.java @@ -0,0 +1,44 @@ +package ladder.domain; + +import ladder.exception.IllegalVerticalLineWidthException; + +import java.util.Set; + +public class VerticalLines { + private final Set verticalLineSet; + private final int maxWidth; + + public VerticalLines(Set verticalLineSet, int maxWidth) { + checkValidVerticalLineWidth(verticalLineSet, maxWidth); + + this.verticalLineSet = verticalLineSet; + this.maxWidth = maxWidth; + } + + private void checkValidVerticalLineWidth(Set verticalLineSet, int maxWidth) { + if (verticalLineSet.stream() + .anyMatch(it -> it.getIndex() >= maxWidth) + ) { + throw new IllegalVerticalLineWidthException(String.format("최대 너비 : %d", maxWidth)); + } + } + + public Set getVerticalLineSet() { + return verticalLineSet; + } + + public int getMaxWidth() { + return maxWidth; + } + + public VerticalLine getVerticalLineByIndex(int index) { + return verticalLineSet.stream() + .filter(it -> it.getIndex() == index) + .findFirst() + .orElse(null); + } + + public int getSize() { + return verticalLineSet.size(); + } +} diff --git a/src/main/java/ladder/domain/Player.java b/src/main/java/ladder/domain/player/Player.java similarity index 93% rename from src/main/java/ladder/domain/Player.java rename to src/main/java/ladder/domain/player/Player.java index 1358c5ba44..6cb175eaef 100644 --- a/src/main/java/ladder/domain/Player.java +++ b/src/main/java/ladder/domain/player/Player.java @@ -1,4 +1,4 @@ -package ladder.domain; +package ladder.domain.player; import ladder.exception.IllegalPlayerNameException; diff --git a/src/main/java/ladder/domain/Players.java b/src/main/java/ladder/domain/player/Players.java similarity index 92% rename from src/main/java/ladder/domain/Players.java rename to src/main/java/ladder/domain/player/Players.java index b75965b95e..8d70145f0e 100644 --- a/src/main/java/ladder/domain/Players.java +++ b/src/main/java/ladder/domain/player/Players.java @@ -1,4 +1,4 @@ -package ladder.domain; +package ladder.domain.player; import java.util.List; diff --git a/src/main/java/ladder/domain/PlayersGenerator.java b/src/main/java/ladder/domain/player/PlayersGenerator.java similarity index 94% rename from src/main/java/ladder/domain/PlayersGenerator.java rename to src/main/java/ladder/domain/player/PlayersGenerator.java index 218c6259cd..f4eb10df41 100644 --- a/src/main/java/ladder/domain/PlayersGenerator.java +++ b/src/main/java/ladder/domain/player/PlayersGenerator.java @@ -1,4 +1,4 @@ -package ladder.domain; +package ladder.domain.player; import java.util.Arrays; import java.util.List; @@ -6,6 +6,7 @@ public class PlayersGenerator { private static final String DEFAULT_SEPARATOR = ","; + private PlayersGenerator() { } diff --git a/src/main/java/ladder/exception/ContinuousHorizontalLineException.java b/src/main/java/ladder/exception/ContinuousHorizontalLineException.java new file mode 100644 index 0000000000..4d7075c650 --- /dev/null +++ b/src/main/java/ladder/exception/ContinuousHorizontalLineException.java @@ -0,0 +1,9 @@ +package ladder.exception; + +public class ContinuousHorizontalLineException extends RuntimeException { + private static final String DEFAULT_MESSAGE = "동일한 높이에서 연속되는 가로선이 있습니다."; + + public ContinuousHorizontalLineException(String message) { + super(String.format("%s %s", DEFAULT_MESSAGE, message)); + } +} diff --git a/src/main/java/ladder/exception/IllegalAdjacentVerticalLinesException.java b/src/main/java/ladder/exception/IllegalAdjacentVerticalLinesException.java new file mode 100644 index 0000000000..37f9a6150e --- /dev/null +++ b/src/main/java/ladder/exception/IllegalAdjacentVerticalLinesException.java @@ -0,0 +1,9 @@ +package ladder.exception; + +public class IllegalAdjacentVerticalLinesException extends RuntimeException { + private static final String DEFAULT_MESSAGE = "인덱스의 차이가 2 이상인 인접하지 않은 VerticalLine으로 생성할 수 없습니다."; + + public IllegalAdjacentVerticalLinesException(String message) { + super(String.format("%s %s", DEFAULT_MESSAGE, message)); + } +} diff --git a/src/main/java/ladder/exception/IllegalHorizontalLineHeightException.java b/src/main/java/ladder/exception/IllegalHorizontalLineHeightException.java new file mode 100644 index 0000000000..f20a154e91 --- /dev/null +++ b/src/main/java/ladder/exception/IllegalHorizontalLineHeightException.java @@ -0,0 +1,9 @@ +package ladder.exception; + +public class IllegalHorizontalLineHeightException extends RuntimeException { + private static final String DEFAULT_MESSAGE = "최대 높이를 초과하는 가로선이 있습니다."; + + public IllegalHorizontalLineHeightException(String message) { + super(String.format("%s %s", DEFAULT_MESSAGE, message)); + } +} diff --git a/src/main/java/ladder/exception/IllegalVerticalLineWidthException.java b/src/main/java/ladder/exception/IllegalVerticalLineWidthException.java new file mode 100644 index 0000000000..f5918b9248 --- /dev/null +++ b/src/main/java/ladder/exception/IllegalVerticalLineWidthException.java @@ -0,0 +1,9 @@ +package ladder.exception; + +public class IllegalVerticalLineWidthException extends RuntimeException { + private static final String DEFAULT_MESSAGE = "최대 너비를 초과하는 세로선이 있습니다."; + + public IllegalVerticalLineWidthException(String message) { + super(String.format("%s %s", DEFAULT_MESSAGE, message)); + } +} diff --git a/src/main/java/ladder/exception/NotEnoughVerticalLinesException.java b/src/main/java/ladder/exception/NotEnoughVerticalLinesException.java new file mode 100644 index 0000000000..fc1b261917 --- /dev/null +++ b/src/main/java/ladder/exception/NotEnoughVerticalLinesException.java @@ -0,0 +1,9 @@ +package ladder.exception; + +public class NotEnoughVerticalLinesException extends RuntimeException { + private static final String DEFAULT_MESSAGE = "최소 두 개 이상의 세로선이 있어야 합니다."; + + public NotEnoughVerticalLinesException(String message) { + super(String.format("%s %s", DEFAULT_MESSAGE, message)); + } +} diff --git a/src/test/java/ladder/domain/AdjacentVerticalLinesTest.java b/src/test/java/ladder/domain/AdjacentVerticalLinesTest.java new file mode 100644 index 0000000000..afd5b22e96 --- /dev/null +++ b/src/test/java/ladder/domain/AdjacentVerticalLinesTest.java @@ -0,0 +1,35 @@ +package ladder.domain; + +import ladder.exception.IllegalAdjacentVerticalLinesException; +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.AssertionsForClassTypes.assertThat; +import static org.assertj.core.api.AssertionsForClassTypes.assertThatThrownBy; + +public class AdjacentVerticalLinesTest { + private final VerticalLine verticalLine0 = new VerticalLine(0); + private final VerticalLine verticalLine1 = new VerticalLine(1); + private final VerticalLine verticalLine2 = new VerticalLine(2); + + @Test + void 인접한_수직선들로_AdjacentVerticalLines를_만들_수_있다() { + AdjacentVerticalLines adjacentVerticalLines = new AdjacentVerticalLines(verticalLine0, verticalLine1); + + assertThat(adjacentVerticalLines.getLeftVerticalLine()).isEqualTo(verticalLine0); + assertThat(adjacentVerticalLines.getRightVerticalLine()).isEqualTo(verticalLine1); + } + + @Test + void 생성_시_순서에_관계없이_left_right를_구분할_수_있다() { + AdjacentVerticalLines adjacentVerticalLines = new AdjacentVerticalLines(verticalLine1, verticalLine0); + + assertThat(adjacentVerticalLines.getLeftVerticalLine()).isEqualTo(verticalLine0); + assertThat(adjacentVerticalLines.getRightVerticalLine()).isEqualTo(verticalLine1); + } + + @Test + void 각_수직선의_index_차이가_2_이상이면_예외가_발생한다() { + assertThatThrownBy(() -> new AdjacentVerticalLines(verticalLine0, verticalLine2)) + .isInstanceOf(IllegalAdjacentVerticalLinesException.class); + } +} diff --git a/src/test/java/ladder/domain/HorizontalLineTest.java b/src/test/java/ladder/domain/HorizontalLineTest.java new file mode 100644 index 0000000000..416f7cce2c --- /dev/null +++ b/src/test/java/ladder/domain/HorizontalLineTest.java @@ -0,0 +1,44 @@ +package ladder.domain; + +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.AssertionsForClassTypes.assertThat; + +public class HorizontalLineTest { + private final VerticalLine verticalLine0 = new VerticalLine(0); + private final VerticalLine verticalLine1 = new VerticalLine(1); + private final VerticalLine verticalLine2 = new VerticalLine(2); + private final AdjacentVerticalLines adjacentVerticalLines = new AdjacentVerticalLines(verticalLine0, verticalLine1); + + @Test + void 특정_인덱스의_세로선을_잇는_HorizontalLine을_만들_수_있다() { + HorizontalLine horizontalLine = new HorizontalLine(adjacentVerticalLines, 0); + + assertThat(horizontalLine.getAdjacentVerticalLines().getLeftVerticalLine()).isEqualTo(verticalLine0); + assertThat(horizontalLine.getAdjacentVerticalLines().getRightVerticalLine()).isEqualTo(verticalLine1); + assertThat(horizontalLine.getHeight()).isEqualTo(0); + } + + @Test + void 왼쪽으로_맞닿은_세로선을_반환할_수_있다() { + HorizontalLine horizontalLine = new HorizontalLine(adjacentVerticalLines, 0); + + assertThat(horizontalLine.getLeftVerticalLine()).isEqualTo(verticalLine0); + } + + @Test + void 오른쪽으로_맞닿은_세로선을_반환할_수_있다() { + HorizontalLine horizontalLine = new HorizontalLine(adjacentVerticalLines, 0); + + assertThat(horizontalLine.getRightVerticalLine()).isEqualTo(verticalLine1); + } + + @Test + void 세로선과_맞닿아있는지_확인할_수_있다() { + HorizontalLine horizontalLine = new HorizontalLine(adjacentVerticalLines, 0); + + assertThat(horizontalLine.isConnected(verticalLine0)).isTrue(); + assertThat(horizontalLine.isConnected(verticalLine1)).isTrue(); + assertThat(horizontalLine.isConnected(verticalLine2)).isFalse(); + } +} diff --git a/src/test/java/ladder/domain/HorizontalLinesTest.java b/src/test/java/ladder/domain/HorizontalLinesTest.java new file mode 100644 index 0000000000..75dd748f2c --- /dev/null +++ b/src/test/java/ladder/domain/HorizontalLinesTest.java @@ -0,0 +1,52 @@ +package ladder.domain; + +import ladder.exception.IllegalHorizontalLineHeightException; +import org.junit.jupiter.api.Test; + +import java.util.Set; + +import static org.assertj.core.api.AssertionsForClassTypes.assertThat; +import static org.assertj.core.api.AssertionsForClassTypes.assertThatThrownBy; + +public class HorizontalLinesTest { + private final VerticalLine verticalLine0 = new VerticalLine(0); + private final VerticalLine verticalLine1 = new VerticalLine(1); + private final AdjacentVerticalLines adjacentVerticalLines = new AdjacentVerticalLines(verticalLine0, verticalLine1); + private final HorizontalLine horizontalLine0 = new HorizontalLine(adjacentVerticalLines, 0); + private final HorizontalLine horizontalLine1 = new HorizontalLine(adjacentVerticalLines, 1); + private final Set horizontalLineSet = Set.of( + horizontalLine0, horizontalLine1 + ); + + @Test + void HorizontalLineSet와_최대_높이로_생성하여_이를_리스트로_반환할_수_있다() { + assertThat(new HorizontalLines(horizontalLineSet, 3) + .getHorizontalLineSet() + .containsAll(horizontalLineSet) + ).isTrue(); + } + + @Test + void 높이별로_HorizontalLineSet를_반환할_수_있다() { + HorizontalLines horizontalLines = new HorizontalLines(horizontalLineSet, 3); + Set horizontalLineSet0 = horizontalLines.getHorizontalLineSetByHeight(0); + Set horizontalLineSet1 = horizontalLines.getHorizontalLineSetByHeight(1); + + assertThat(horizontalLineSet0.contains(horizontalLine0)).isTrue(); + assertThat(horizontalLineSet0.contains(horizontalLine1)).isFalse(); + assertThat(horizontalLineSet1.contains(horizontalLine0)).isFalse(); + assertThat(horizontalLineSet1.contains(horizontalLine1)).isTrue(); + } + + @Test + void 최대_높이를_반환할_수_있다() { + assertThat(new HorizontalLines(horizontalLineSet, 3).getMaxHeight()).isEqualTo(3); + } + + @Test + void 최대_높이를_초과하는_horizontalLine이_있으면_예외가_발생한다() { + HorizontalLine horizontalLine = new HorizontalLine(adjacentVerticalLines, 5); + assertThatThrownBy(() -> new HorizontalLines(Set.of(horizontalLine), 3)) + .isInstanceOf(IllegalHorizontalLineHeightException.class); + } +} diff --git a/src/test/java/ladder/domain/LadderTest.java b/src/test/java/ladder/domain/LadderTest.java new file mode 100644 index 0000000000..6171447470 --- /dev/null +++ b/src/test/java/ladder/domain/LadderTest.java @@ -0,0 +1,75 @@ +package ladder.domain; + +import ladder.exception.ContinuousHorizontalLineException; +import ladder.exception.NotEnoughVerticalLinesException; +import org.junit.jupiter.api.Test; + +import java.util.Set; + +import static org.assertj.core.api.AssertionsForClassTypes.assertThat; +import static org.assertj.core.api.AssertionsForClassTypes.assertThatThrownBy; + +public class LadderTest { + private final int maxWidth = 3; + private final int maxHeight = 2; + private final VerticalLine verticalLine0 = new VerticalLine(0); + private final VerticalLine verticalLine1 = new VerticalLine(1); + private final AdjacentVerticalLines adjacentVerticalLines = new AdjacentVerticalLines(verticalLine0, verticalLine1); + private final HorizontalLine horizontalLine = new HorizontalLine(adjacentVerticalLines, 0); + private final VerticalLines verticalLines = new VerticalLines(Set.of(verticalLine0, verticalLine1), maxWidth); + private final HorizontalLines horizontalLines = new HorizontalLines(Set.of(horizontalLine), maxHeight); + + @Test + void 사다리는_최대_높이를_반환할_수_있다() { + assertThat(new Ladder(verticalLines, horizontalLines).getHeight()).isEqualTo(maxHeight); + } + + @Test + void 사다리는_최대_너비를_반환할_수_있다() { + assertThat(new Ladder(verticalLines, horizontalLines).getWidth()).isEqualTo(maxWidth); + } + + @Test + void 사다리는_세로선들을_반환할_수_있다() { + assertThat( + new Ladder(verticalLines, horizontalLines).getVerticalLines() + .getVerticalLineSet() + .containsAll(Set.of(verticalLine0, verticalLine1)) + ).isTrue(); + } + + @Test + void 사다리는_가로선들을_반환할_수_있다() { + assertThat( + new Ladder(verticalLines, horizontalLines).getHorizontalLines() + .getHorizontalLineSet() + .contains(horizontalLine) + ).isTrue(); + } + + @Test + void 동일한_높이에서_연속되는_가로선이_존재하면_예외가_발생한다() { + VerticalLine verticalLine2 = new VerticalLine(2); + AdjacentVerticalLines adjacentVerticalLines12 = new AdjacentVerticalLines(verticalLine1, verticalLine2); + HorizontalLine wrongHorizontalLine = new HorizontalLine(adjacentVerticalLines12, 0); + + assertThatThrownBy(() -> + new Ladder( + new VerticalLines( + Set.of(verticalLine0, verticalLine1, verticalLine2), + maxWidth + ), + new HorizontalLines( + Set.of(horizontalLine, wrongHorizontalLine), + maxHeight + ) + ) + ).isInstanceOf(ContinuousHorizontalLineException.class); + } + + @Test + void 세로선이_하나_이하이면_예외가_발생한다() { + assertThatThrownBy(() -> new Ladder(new VerticalLines(Set.of(verticalLine0), 1), horizontalLines)) + .isInstanceOf(NotEnoughVerticalLinesException.class); + } +} diff --git a/src/test/java/ladder/domain/VerticalLineTest.java b/src/test/java/ladder/domain/VerticalLineTest.java new file mode 100644 index 0000000000..76ef54b1af --- /dev/null +++ b/src/test/java/ladder/domain/VerticalLineTest.java @@ -0,0 +1,12 @@ +package ladder.domain; + +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.AssertionsForClassTypes.assertThat; + +public class VerticalLineTest { + @Test + void 인덱스를_지정하여_VerticalLine을_만들_수_있다() { + assertThat(new VerticalLine(3).getIndex()).isEqualTo(3); + } +} diff --git a/src/test/java/ladder/domain/VerticalLinesTest.java b/src/test/java/ladder/domain/VerticalLinesTest.java new file mode 100644 index 0000000000..7a639caf32 --- /dev/null +++ b/src/test/java/ladder/domain/VerticalLinesTest.java @@ -0,0 +1,48 @@ +package ladder.domain; + +import ladder.exception.IllegalVerticalLineWidthException; +import org.junit.jupiter.api.Test; + +import java.util.Set; + +import static org.assertj.core.api.AssertionsForClassTypes.assertThat; +import static org.assertj.core.api.AssertionsForClassTypes.assertThatThrownBy; + +public class VerticalLinesTest { + private final VerticalLine verticalLine0 = new VerticalLine(0); + private final VerticalLine verticalLine1 = new VerticalLine(1); + private final Set verticalLineSet = Set.of(verticalLine0, verticalLine1); + + @Test + void VerticalLineSet를_반환할_수_있다() { + assertThat(new VerticalLines(verticalLineSet, 2) + .getVerticalLineSet() + .containsAll(verticalLineSet) + ).isTrue(); + } + + @Test + void 최대_너비를_반환할_수_있다() { + assertThat(new VerticalLines(verticalLineSet, 2).getMaxWidth()).isEqualTo(2); + } + + @Test + void 최대_너비를_초과하는_verticalLine이_있으면_예외가_발생한다() { + VerticalLine verticalLine = new VerticalLine(5); + assertThatThrownBy(() -> new VerticalLines(Set.of(verticalLine), 3)) + .isInstanceOf(IllegalVerticalLineWidthException.class); + } + + @Test + void 주어진_index에_해당하는_VerticalLine을_반환할_수_있다() { + VerticalLines verticalLines = new VerticalLines(verticalLineSet, 2); + + assertThat(verticalLines.getVerticalLineByIndex(0)).isEqualTo(verticalLine0); + assertThat(verticalLines.getVerticalLineByIndex(1)).isEqualTo(verticalLine1); + } + + @Test + void 주어진_index에_해당하는_VerticalLine이_없으면_null을_반환한다() { + assertThat(new VerticalLines(verticalLineSet, 2).getVerticalLineByIndex(5)).isNull(); + } +} diff --git a/src/test/java/ladder/domain/PlayerTest.java b/src/test/java/ladder/domain/player/PlayerTest.java similarity index 74% rename from src/test/java/ladder/domain/PlayerTest.java rename to src/test/java/ladder/domain/player/PlayerTest.java index a3b43cead1..89df50bb0d 100644 --- a/src/test/java/ladder/domain/PlayerTest.java +++ b/src/test/java/ladder/domain/player/PlayerTest.java @@ -1,9 +1,10 @@ -package ladder.domain; +package ladder.domain.player; import ladder.exception.IllegalPlayerNameException; import org.junit.jupiter.api.Test; -import static org.assertj.core.api.AssertionsForClassTypes.*; +import static org.assertj.core.api.AssertionsForClassTypes.assertThat; +import static org.assertj.core.api.AssertionsForClassTypes.assertThatThrownBy; public class PlayerTest { @Test diff --git a/src/test/java/ladder/domain/PlayersGeneratorTest.java b/src/test/java/ladder/domain/player/PlayersGeneratorTest.java similarity index 94% rename from src/test/java/ladder/domain/PlayersGeneratorTest.java rename to src/test/java/ladder/domain/player/PlayersGeneratorTest.java index 9de7dd69fe..eefbadb5f2 100644 --- a/src/test/java/ladder/domain/PlayersGeneratorTest.java +++ b/src/test/java/ladder/domain/player/PlayersGeneratorTest.java @@ -1,4 +1,4 @@ -package ladder.domain; +package ladder.domain.player; import org.junit.jupiter.api.Test; diff --git a/src/test/java/ladder/domain/PlayersTest.java b/src/test/java/ladder/domain/player/PlayersTest.java similarity index 95% rename from src/test/java/ladder/domain/PlayersTest.java rename to src/test/java/ladder/domain/player/PlayersTest.java index 72bff73ee3..8f9d573c39 100644 --- a/src/test/java/ladder/domain/PlayersTest.java +++ b/src/test/java/ladder/domain/player/PlayersTest.java @@ -1,4 +1,4 @@ -package ladder.domain; +package ladder.domain.player; import org.junit.jupiter.api.Test; From 59d1c9ba2c336991ebeb17781f3073de054e8805 Mon Sep 17 00:00:00 2001 From: SimJung Date: Wed, 17 May 2023 22:10:14 +0900 Subject: [PATCH 14/14] =?UTF-8?q?feat=20:=20LadderGenerator=20=EA=B5=AC?= =?UTF-8?q?=ED=98=84=20=EB=B0=8F=20main=20=EA=B5=AC=EC=84=B1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - view 패키지 추가 --- src/main/java/ladder/Main.java | 24 +++++++ .../java/ladder/domain/HorizontalLine.java | 12 ++++ .../java/ladder/domain/HorizontalLines.java | 6 +- src/main/java/ladder/domain/Ladder.java | 2 +- .../ladder/domain/LadderGenerateStrategy.java | 5 ++ .../java/ladder/domain/LadderGenerator.java | 71 +++++++++++++++++++ .../java/ladder/domain/VerticalLines.java | 11 ++- .../IllegalHorizontalLineHeightException.java | 2 +- .../IllegalLadderParameterException.java | 9 +++ src/main/java/ladder/view/InputView.java | 20 ++++++ src/main/java/ladder/view/ResultView.java | 56 +++++++++++++++ .../ladder/domain/HorizontalLineTest.java | 8 +++ .../ladder/domain/HorizontalLinesTest.java | 6 ++ .../ladder/domain/LadderGeneratorTest.java | 41 +++++++++++ .../java/ladder/domain/VerticalLinesTest.java | 5 ++ 15 files changed, 274 insertions(+), 4 deletions(-) create mode 100644 src/main/java/ladder/Main.java create mode 100644 src/main/java/ladder/domain/LadderGenerateStrategy.java create mode 100644 src/main/java/ladder/domain/LadderGenerator.java create mode 100644 src/main/java/ladder/exception/IllegalLadderParameterException.java create mode 100644 src/main/java/ladder/view/InputView.java create mode 100644 src/main/java/ladder/view/ResultView.java create mode 100644 src/test/java/ladder/domain/LadderGeneratorTest.java diff --git a/src/main/java/ladder/Main.java b/src/main/java/ladder/Main.java new file mode 100644 index 0000000000..34713d0885 --- /dev/null +++ b/src/main/java/ladder/Main.java @@ -0,0 +1,24 @@ +package ladder; + +import ladder.domain.Ladder; +import ladder.domain.LadderGenerator; +import ladder.domain.player.Players; +import ladder.domain.player.PlayersGenerator; +import ladder.view.InputView; +import ladder.view.ResultView; + +public class Main { + public static void main(String[] args) { + Players players = PlayersGenerator.create(InputView.getPlayerNames()); + int width = players.getPlayerNumber(); + System.out.println(); + + int height = InputView.getLadderHeight(); + System.out.println(); + + Ladder ladder = new LadderGenerator().generate(height, width); + ResultView.showResultMessage(); + ResultView.showPlayers(players); + ResultView.showLadder(ladder); + } +} diff --git a/src/main/java/ladder/domain/HorizontalLine.java b/src/main/java/ladder/domain/HorizontalLine.java index 135b38510c..b7cf1d7367 100644 --- a/src/main/java/ladder/domain/HorizontalLine.java +++ b/src/main/java/ladder/domain/HorizontalLine.java @@ -1,14 +1,26 @@ package ladder.domain; +import ladder.exception.IllegalHorizontalLineHeightException; + public class HorizontalLine { + static final int MINIMUM_HEIGHT = 0; + private final AdjacentVerticalLines adjacentVerticalLines; private final int height; public HorizontalLine(AdjacentVerticalLines adjacentVerticalLines, int height) { + checkHeight(height); + this.adjacentVerticalLines = adjacentVerticalLines; this.height = height; } + private void checkHeight(int height) { + if (height < MINIMUM_HEIGHT) { + throw new IllegalHorizontalLineHeightException(String.format("최소 높이 : %d", MINIMUM_HEIGHT)); + } + } + public AdjacentVerticalLines getAdjacentVerticalLines() { return adjacentVerticalLines; } diff --git a/src/main/java/ladder/domain/HorizontalLines.java b/src/main/java/ladder/domain/HorizontalLines.java index 745bc3abe2..8498a55d46 100644 --- a/src/main/java/ladder/domain/HorizontalLines.java +++ b/src/main/java/ladder/domain/HorizontalLines.java @@ -25,7 +25,7 @@ private void checkValidHorizontalLineHeight(Set horizontalLineSe } public Set getHorizontalLineSet() { - return horizontalLineSet; + return Set.copyOf(horizontalLineSet); } public Set getHorizontalLineSetByHeight(int height) { @@ -37,4 +37,8 @@ public Set getHorizontalLineSetByHeight(int height) { public int getMaxHeight() { return maxHeight; } + + public int getSize() { + return horizontalLineSet.size(); + } } diff --git a/src/main/java/ladder/domain/Ladder.java b/src/main/java/ladder/domain/Ladder.java index a6998ff783..98f586122c 100644 --- a/src/main/java/ladder/domain/Ladder.java +++ b/src/main/java/ladder/domain/Ladder.java @@ -6,7 +6,7 @@ import java.util.Set; public class Ladder { - private static final int MINIMUM_VERTICAL_LINES_QUANTITY = 2; + static final int MINIMUM_VERTICAL_LINES_QUANTITY = 2; private final VerticalLines verticalLines; private final HorizontalLines horizontalLines; diff --git a/src/main/java/ladder/domain/LadderGenerateStrategy.java b/src/main/java/ladder/domain/LadderGenerateStrategy.java new file mode 100644 index 0000000000..275bf245ea --- /dev/null +++ b/src/main/java/ladder/domain/LadderGenerateStrategy.java @@ -0,0 +1,5 @@ +package ladder.domain; + +public interface LadderGenerateStrategy { + boolean canGenerate(); +} diff --git a/src/main/java/ladder/domain/LadderGenerator.java b/src/main/java/ladder/domain/LadderGenerator.java new file mode 100644 index 0000000000..e76f9201d4 --- /dev/null +++ b/src/main/java/ladder/domain/LadderGenerator.java @@ -0,0 +1,71 @@ +package ladder.domain; + +import ladder.exception.IllegalLadderParameterException; + +import java.util.HashSet; +import java.util.Set; + +public class LadderGenerator { + private static final double DEFAULT_CHANCE = 0.5; + + private final LadderGenerateStrategy ladderGenerateStrategy; + + public LadderGenerator() { + this.ladderGenerateStrategy = () -> Math.random() < DEFAULT_CHANCE; + } + + public LadderGenerator(LadderGenerateStrategy ladderGenerateStrategy) { + this.ladderGenerateStrategy = ladderGenerateStrategy; + } + + public Ladder generate(int height, int width) { + checkHeightAndWidth(height, width); + + VerticalLines verticalLines = VerticalLines.create(width); + HorizontalLines horizontalLines = createHorizontalLines(verticalLines, height); + + return new Ladder(verticalLines, horizontalLines); + } + + private HorizontalLines createHorizontalLines(VerticalLines verticalLines, int height) { + HashSet horizontalLineHashSet = new HashSet<>(); + + for (int i = 0; i < height; i++) { + Set sameHeightHorizontalLineSet = createSameHeightHorizontalLineSet(verticalLines, i); + horizontalLineHashSet.addAll(sameHeightHorizontalLineSet); + } + + return new HorizontalLines(horizontalLineHashSet, height); + } + + private Set createSameHeightHorizontalLineSet(VerticalLines verticalLines, int height) { + HashSet sameHeightHorizontalLineHashSet = new HashSet<>(); + + for (int i = 0; i < verticalLines.getMaxWidth() - 1; i++) { + VerticalLine nowVerticalLine = verticalLines.getVerticalLineByIndex(i); + VerticalLine nextVerticalLine = verticalLines.getVerticalLineByIndex(i + 1); + + boolean notExistPreviousHorizontalLine = sameHeightHorizontalLineHashSet.stream() + .noneMatch(horizontalLine -> + horizontalLine.getRightVerticalLine() == nowVerticalLine + ); + + if (notExistPreviousHorizontalLine && ladderGenerateStrategy.canGenerate()) { + sameHeightHorizontalLineHashSet.add( + new HorizontalLine( + new AdjacentVerticalLines(nowVerticalLine, nextVerticalLine), + height + ) + ); + } + } + return sameHeightHorizontalLineHashSet; + } + + private void checkHeightAndWidth(int height, int width) { + if (height < HorizontalLine.MINIMUM_HEIGHT + || width < Ladder.MINIMUM_VERTICAL_LINES_QUANTITY) { + throw new IllegalLadderParameterException(String.format("입력된 높이 : %d, 입력된 너비 : %d", height, width)); + } + } +} diff --git a/src/main/java/ladder/domain/VerticalLines.java b/src/main/java/ladder/domain/VerticalLines.java index c616c153c4..e9931f7255 100644 --- a/src/main/java/ladder/domain/VerticalLines.java +++ b/src/main/java/ladder/domain/VerticalLines.java @@ -2,6 +2,7 @@ import ladder.exception.IllegalVerticalLineWidthException; +import java.util.HashSet; import java.util.Set; public class VerticalLines { @@ -24,7 +25,7 @@ private void checkValidVerticalLineWidth(Set verticalLineSet, int } public Set getVerticalLineSet() { - return verticalLineSet; + return Set.copyOf(verticalLineSet); } public int getMaxWidth() { @@ -41,4 +42,12 @@ public VerticalLine getVerticalLineByIndex(int index) { public int getSize() { return verticalLineSet.size(); } + + public static VerticalLines create(int count) { + HashSet verticalLineHashSet = new HashSet<>(); + for (int i = 0; i < count; i++) { + verticalLineHashSet.add(new VerticalLine(i)); + } + return new VerticalLines(verticalLineHashSet, count); + } } diff --git a/src/main/java/ladder/exception/IllegalHorizontalLineHeightException.java b/src/main/java/ladder/exception/IllegalHorizontalLineHeightException.java index f20a154e91..30a17a56cd 100644 --- a/src/main/java/ladder/exception/IllegalHorizontalLineHeightException.java +++ b/src/main/java/ladder/exception/IllegalHorizontalLineHeightException.java @@ -1,7 +1,7 @@ package ladder.exception; public class IllegalHorizontalLineHeightException extends RuntimeException { - private static final String DEFAULT_MESSAGE = "최대 높이를 초과하는 가로선이 있습니다."; + private static final String DEFAULT_MESSAGE = "적절하지 않은 높이의 가로선입니다."; public IllegalHorizontalLineHeightException(String message) { super(String.format("%s %s", DEFAULT_MESSAGE, message)); diff --git a/src/main/java/ladder/exception/IllegalLadderParameterException.java b/src/main/java/ladder/exception/IllegalLadderParameterException.java new file mode 100644 index 0000000000..24013e3503 --- /dev/null +++ b/src/main/java/ladder/exception/IllegalLadderParameterException.java @@ -0,0 +1,9 @@ +package ladder.exception; + +public class IllegalLadderParameterException extends RuntimeException { + private static final String DEFAULT_MESSAGE = "높이는 0 이상, 너비는 2 이상이 되어야 합니다."; + + public IllegalLadderParameterException(String message) { + super(String.format("%s %s", DEFAULT_MESSAGE, message)); + } +} diff --git a/src/main/java/ladder/view/InputView.java b/src/main/java/ladder/view/InputView.java new file mode 100644 index 0000000000..4db1b76bfc --- /dev/null +++ b/src/main/java/ladder/view/InputView.java @@ -0,0 +1,20 @@ +package ladder.view; + +import java.util.Scanner; + +public class InputView { + private static final Scanner scanner = new Scanner(System.in); + + private InputView() { + } + + public static String getPlayerNames() { + System.out.println("참여할 사람 이름을 입력하세요. (이름은 쉼표(,)로 구분하세요"); + return scanner.nextLine(); + } + + public static int getLadderHeight() { + System.out.println("최대 사다리 높이는 몇 개인가요?"); + return Integer.parseInt(scanner.nextLine()); + } +} diff --git a/src/main/java/ladder/view/ResultView.java b/src/main/java/ladder/view/ResultView.java new file mode 100644 index 0000000000..de6e3021a4 --- /dev/null +++ b/src/main/java/ladder/view/ResultView.java @@ -0,0 +1,56 @@ +package ladder.view; + +import ladder.domain.Ladder; +import ladder.domain.player.Players; + +import java.util.Arrays; + +public class ResultView { + private static final int HORIZONTAL_CHARACTER_LENGTH = 6; + + private ResultView() { + } + + public static void showResultMessage() { + System.out.println("실행결과\n"); + } + + public static void showPlayers(Players players) { + System.out.print(" "); + players.getPlayerList() + .forEach(player -> System.out.printf("%-6s", player.getName())); + System.out.println(); + } + + public static void showLadder(Ladder ladder) { + int maxHeight = ladder.getHeight(); + int maxWidth = ladder.getWidth() * HORIZONTAL_CHARACTER_LENGTH; + char[][] ladderCharacters = new char[maxHeight][maxWidth]; + Arrays.stream(ladderCharacters).forEach(it -> Arrays.fill(it, ' ')); + + for (int i = 0; i < maxHeight; i++) { + int height = i; + ladder.getVerticalLines() + .getVerticalLineSet() + .stream() + .map(it -> (it.getIndex() + 1) * HORIZONTAL_CHARACTER_LENGTH - 1) + .forEach(it -> ladderCharacters[height][it] = '|'); + + ladder.getHorizontalLines().getHorizontalLineSetByHeight(height) + .forEach(horizontalLine -> { + int from = horizontalLine.getLeftVerticalLine().getIndex(); + int to = horizontalLine.getRightVerticalLine().getIndex(); + for (int j = (from + 1) * HORIZONTAL_CHARACTER_LENGTH; j < (to + 1) * HORIZONTAL_CHARACTER_LENGTH - 1; j++) { + ladderCharacters[height][j] = '-'; + } + }); + } + + for (int i = 0; i < ladder.getHeight(); i++) { + for (int j = 0; j < ladder.getWidth() * HORIZONTAL_CHARACTER_LENGTH; j++) { + System.out.print(ladderCharacters[i][j]); + } + System.out.println(); + } + } +} diff --git a/src/test/java/ladder/domain/HorizontalLineTest.java b/src/test/java/ladder/domain/HorizontalLineTest.java index 416f7cce2c..793d80133e 100644 --- a/src/test/java/ladder/domain/HorizontalLineTest.java +++ b/src/test/java/ladder/domain/HorizontalLineTest.java @@ -1,8 +1,10 @@ package ladder.domain; +import ladder.exception.IllegalHorizontalLineHeightException; import org.junit.jupiter.api.Test; import static org.assertj.core.api.AssertionsForClassTypes.assertThat; +import static org.assertj.core.api.AssertionsForClassTypes.assertThatThrownBy; public class HorizontalLineTest { private final VerticalLine verticalLine0 = new VerticalLine(0); @@ -41,4 +43,10 @@ public class HorizontalLineTest { assertThat(horizontalLine.isConnected(verticalLine1)).isTrue(); assertThat(horizontalLine.isConnected(verticalLine2)).isFalse(); } + + @Test + void 음수_높이를_가지면_예외가_발생한다() { + assertThatThrownBy(() -> new HorizontalLine(adjacentVerticalLines, -1)) + .isInstanceOf(IllegalHorizontalLineHeightException.class); + } } diff --git a/src/test/java/ladder/domain/HorizontalLinesTest.java b/src/test/java/ladder/domain/HorizontalLinesTest.java index 75dd748f2c..030aa169e6 100644 --- a/src/test/java/ladder/domain/HorizontalLinesTest.java +++ b/src/test/java/ladder/domain/HorizontalLinesTest.java @@ -49,4 +49,10 @@ public class HorizontalLinesTest { assertThatThrownBy(() -> new HorizontalLines(Set.of(horizontalLine), 3)) .isInstanceOf(IllegalHorizontalLineHeightException.class); } + + @Test + void HorizontalLine들의_갯수를_반환할_수_있다() { + HorizontalLines horizontalLines = new HorizontalLines(horizontalLineSet, 3); + assertThat(horizontalLines.getSize()).isEqualTo(2); + } } diff --git a/src/test/java/ladder/domain/LadderGeneratorTest.java b/src/test/java/ladder/domain/LadderGeneratorTest.java new file mode 100644 index 0000000000..eac917eb7a --- /dev/null +++ b/src/test/java/ladder/domain/LadderGeneratorTest.java @@ -0,0 +1,41 @@ +package ladder.domain; + +import ladder.exception.IllegalLadderParameterException; +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.AssertionsForClassTypes.assertThat; +import static org.assertj.core.api.AssertionsForClassTypes.assertThatThrownBy; + +public class LadderGeneratorTest { + @Test + void 최대_높이에_음수를_입력하면_예외가_발생한다() { + assertThatThrownBy(() -> new LadderGenerator().generate(-1, 2)) + .isInstanceOf(IllegalLadderParameterException.class); + } + + @Test + void 최대_너비에_1_이하의_값을_입력하면_예외가_발생한다() { + assertThatThrownBy(() -> new LadderGenerator().generate(2, 1)) + .isInstanceOf(IllegalLadderParameterException.class); + } + + @Test + void 최대_높이와_최대_너비를_지정하면_사다리를_만들_수_있다() { + int maxHeight = 2; + int maxWidth = 2; + LadderGenerator LadderGenerator = new LadderGenerator(); + Ladder ladder = LadderGenerator.generate(maxHeight, maxWidth); + + assertThat(ladder.getHeight()).isEqualTo(maxHeight); + assertThat(ladder.getWidth()).isEqualTo(maxWidth); + assertThat(ladder.getVerticalLines().getSize()).isEqualTo(2); + } + + @Test + void 사다리_생성_전략에_따라_사다리가_생성된다() { + LadderGenerator LadderGenerator = new LadderGenerator(() -> false); + Ladder ladder = LadderGenerator.generate(2, 2); + + assertThat(ladder.getHorizontalLines().getSize()).isEqualTo(0); + } +} diff --git a/src/test/java/ladder/domain/VerticalLinesTest.java b/src/test/java/ladder/domain/VerticalLinesTest.java index 7a639caf32..b983a43253 100644 --- a/src/test/java/ladder/domain/VerticalLinesTest.java +++ b/src/test/java/ladder/domain/VerticalLinesTest.java @@ -45,4 +45,9 @@ public class VerticalLinesTest { void 주어진_index에_해당하는_VerticalLine이_없으면_null을_반환한다() { assertThat(new VerticalLines(verticalLineSet, 2).getVerticalLineByIndex(5)).isNull(); } + + @Test + void 숫자_만큼의_VerticalLine들을_만들_수_있다() { + assertThat(VerticalLines.create(3).getSize()).isEqualTo(3); + } }