Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

2주차 미션 / 서버 3조 김윤서 #46

Open
wants to merge 10 commits into
base: main
Choose a base branch
from
8 changes: 0 additions & 8 deletions src/main/java/Ladder.java

This file was deleted.

16 changes: 16 additions & 0 deletions src/main/java/ladder/Direction.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
package ladder;

public enum Direction {

LEFT(-1), RIGHT(1), NONE(0);

private final int value;

Direction(int value) {
this.value = value;
}

public int getValue() {
return value;
}
}
19 changes: 19 additions & 0 deletions src/main/java/ladder/ExceptionMessage.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package ladder;

public enum ExceptionMessage {

INVALID_LADDER_POSITION("사다리 위치는 1이상 자연수입니다."),
INVALID_LADDER_NUMBER("사다리의 행과 열은 2 이상이어야 합니다."),
INVALID_POSITION("유효하지 않은 위치입니다."),
INVALID_DRAW_POSITION("사다리를 그릴 수 없는 위치입니다.");

private final String message;

ExceptionMessage(String message) {
this.message = message;
}

public String getMessage() {
return message;
}
}
25 changes: 25 additions & 0 deletions src/main/java/ladder/GreaterThanOne.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
package ladder;

public class GreaterThanOne {

private final int number;

public GreaterThanOne(int number) {
this.number = number;
}

public static GreaterThanOne from(int number) {
if (!isGreaterThanOne(number)) {
throw new IllegalArgumentException(ExceptionMessage.INVALID_LADDER_NUMBER.getMessage());
}
return new GreaterThanOne(number);
}

private static boolean isGreaterThanOne(int number) {
return number > 1;
}

public int getNumber() {
return number;
}
}
6 changes: 6 additions & 0 deletions src/main/java/ladder/LadderCreatorInterface.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
package ladder;

public interface LadderCreatorInterface {
Row[] getRows();
void drawLine(Position row, Position col);
}
16 changes: 16 additions & 0 deletions src/main/java/ladder/LadderGame.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
package ladder;

public class LadderGame {

private final LadderCreatorInterface ladderCreator;

public LadderGame(LadderCreatorInterface ladderCreator) {
this.ladderCreator = ladderCreator;
}

public int run(Position position) {
LadderRunner ladderRunner = new LadderRunner(ladderCreator.getRows());
ladderRunner.run(position);
return position.getPosition();
}
}
11 changes: 11 additions & 0 deletions src/main/java/ladder/LadderGameFactory.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
package ladder;

import ladder.creator.LadderAutoCreator;

public class LadderGameFactory {

public static LadderGame createRandomLadderGame(GreaterThanOne numberOfRow, GreaterThanOne numberOfPerson) {
LadderCreatorInterface ladderCreator = new LadderAutoCreator(numberOfRow, numberOfPerson);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

팩토리 잘 만드신 것 같아요. game 객체를 만드는 코드를 한 곳에서 관리할 수 있으니 수정이 편해지겠네요!

return new LadderGame(ladderCreator);
}
}
36 changes: 36 additions & 0 deletions src/main/java/ladder/LadderRunner.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
package ladder;

public class LadderRunner {

private final Row[] rows;

public LadderRunner(Row[] rows) {
this.rows = rows;
}

public int run(Position position) {
for (int i = 0; i < rows.length; i++) {
System.out.println("Before");
printLadder(position, i);
System.out.println();

rows[i].nextPosition(position);

System.out.println("After");
printLadder(position, i);
System.out.println();
}
return position.getPosition();
}

private void printLadder(Position position, int currentRow) {
StringBuilder ladderBuilder = new StringBuilder();

for (int i = 0; i < rows.length; i++) {
ladderBuilder.append(rows[i].printRow(position, i == currentRow));

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

음 제어 변수로 별을 찍을지 결정하는 것 괜찮은 것 같은데, 이런 제어 결합도는 혼란을 일으킬 수 있으니 주의해서 사용해야할 것 같습니다.

ladderBuilder.append("\n");
}

System.out.print(ladderBuilder.toString());
}
}
55 changes: 55 additions & 0 deletions src/main/java/ladder/Node.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
package ladder;

import static ladder.Direction.*;

public class Node {

private Direction direction;

private Node(Direction direction) {
this.direction = direction;
}

public Direction getDirection() {
return direction;
}

public static Node from(Direction direction) {
return new Node(direction);
}

public void setRightNode(Position position) {
direction = RIGHT;
}

public void setLeftNode(Position position) {
direction = LEFT;
}

public void move(Position position) {
if (isRight()) {
position.next();
return;
}
if (isLeft()) {
position.prev();
return;
}
}

public boolean isAlreadySetDirection() {
return isNone();
}

public boolean isRight() {
return direction == RIGHT;
}

public boolean isLeft() {
return direction == LEFT;
}

public boolean isNone() {
return direction == NONE;
}
}
45 changes: 45 additions & 0 deletions src/main/java/ladder/Position.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
package ladder;

public class Position {

private int position;

private Position(int position) {
this.position = position;
}

public int getPosition() {
return position;
}

public static Position from(int position) {
validatePosition(position);
return new Position(position);
}

public boolean isBiggerThan(int position) {
return this.position > position;
}

public boolean isSmallerThan(int position) {
return this.position < position;
}

public void next() {
position++;
}

public void prev() {
position--;
}

private static void validatePosition(int position) {
if (!isPosition(position)) {
throw new IllegalArgumentException(ExceptionMessage.INVALID_LADDER_POSITION.getMessage());
}
}

private static boolean isPosition(int position) {
return position >= 0;
}
}
90 changes: 90 additions & 0 deletions src/main/java/ladder/Row.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
package ladder;

import static ladder.Direction.*;

public class Row {

Node[] nodes;

public Row(GreaterThanOne numberOfPerson) {
nodes = new Node[numberOfPerson.getNumber()];
for (int i = 0; i < numberOfPerson.getNumber(); i++) {
nodes[i] = Node.from(NONE);
}
}

public boolean canDrawLineAt(int col) {
if (col < 0 || col >= nodes.length - 1) {
return false;
}
return nodes[col].isNone() && nodes[col + 1].isNone();
}

public void drawLine(Position startPosition) {
validateDrawLinePosition(startPosition);

setDirectionBetweenNextPosition(startPosition);
}

private void setDirectionBetweenNextPosition(Position position) {
nodes[position.getPosition()].setRightNode(position);
position.next();
nodes[position.getPosition()].setLeftNode(position);
}

public void nextPosition(Position position) {
validatePosition(position);

nodes[position.getPosition()].move(position);
}

public String printRow(Position position, boolean isCurrentRow) {
StringBuilder rowBuilder = new StringBuilder();

for (int i = 0; i < nodes.length; i++) {
rowBuilder.append(getNodeIndex(i))
.append((isCurrentRow && i == position.getPosition()) ? "*" : "")

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

position 객체의 내부 값이 getter로 노출되네요. 메소드 내부에서 값 비교를 하면 캡슐화를 이룰 수 있지 않을까요?

.append(i < nodes.length - 1 ? " " : "");
}
return rowBuilder.toString();
}

private void validatePosition(Position position) {
if (position.isBiggerThan(nodes.length - 1)) {
throw new IllegalArgumentException(ExceptionMessage.INVALID_POSITION.getMessage());
}
}

private void validateDrawLinePosition(Position startPosition) {
if (isInvalidPosition(startPosition) || isLineAtPosition(startPosition) || isLineAtNextPosition(startPosition)) {
throw new IllegalArgumentException(ExceptionMessage.INVALID_DRAW_POSITION.getMessage());
}
}

private boolean isInvalidPosition(Position startPosition) {
return startPosition.isBiggerThan(nodes.length - 1);
}

private boolean isLineAtPosition(Position startPosition) {
return !nodes[startPosition.getPosition()].isAlreadySetDirection();
}

private boolean isLineAtNextPosition(Position startPosition) {
startPosition.next();
boolean IsLineAtPosition = !nodes[startPosition.getPosition()].isAlreadySetDirection();
startPosition.prev();
return IsLineAtPosition;
}

private String getNodeIndex(int index) {

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Node에 Direction이 있고 어떤 값을 가지는지 알아야 해서 다른 객체와의 결합도가 늘어난 것 같아요. 캡슐화를 적용해볼까요?

switch (nodes[index].getDirection()) {
case RIGHT:
return "1";
case LEFT:
return "-1";
case NONE:
default:
return "0";
}
}
}
50 changes: 50 additions & 0 deletions src/main/java/ladder/creator/LadderAutoCreator.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
package ladder.creator;

import ladder.GreaterThanOne;
import ladder.LadderCreatorInterface;
import ladder.Position;
import ladder.Row;

import java.util.Random;

public class LadderAutoCreator implements LadderCreatorInterface {

private final Row[] rows;
private final int numberOfLines;
private final Random random = new Random();

public LadderAutoCreator(GreaterThanOne numberOfRow, GreaterThanOne numberOfPerson) {
rows = new Row[numberOfRow.getNumber()];

numberOfLines = (int) (numberOfRow.getNumber() * numberOfPerson.getNumber() * 0.3);

for (int i = 0; i < numberOfRow.getNumber(); i++) {
rows[i] = new Row(numberOfPerson);
}

createRandomLines(numberOfPerson);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

객체 생성 시에 랜덤 사다리를 그리는 것 괜찮네요!

}

private void createRandomLines(GreaterThanOne numberOfPerson) {
int linesDrawn = 0;
while (linesDrawn < numberOfLines) {
int randomRow = random.nextInt(rows.length);
int randomCol = random.nextInt(numberOfPerson.getNumber() - 1);

Position position = Position.from(randomCol);

if (rows[randomRow].canDrawLineAt(position.getPosition())) {
rows[randomRow].drawLine(position);
linesDrawn++;
}
Comment on lines +30 to +39
Copy link

@JangIkhwan JangIkhwan Sep 28, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

랜덤하게 그리는 로직이 깔끔하네요!

}
}

public void drawLine(Position row, Position col) {
rows[row.getPosition()].drawLine(col);
}

public Row[] getRows() {
return rows;
}
}
Loading