-
Notifications
You must be signed in to change notification settings - Fork 18
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
[사다리 미션] 신혜빈 미션 제출합니다. #20
base: shin378378
Are you sure you want to change the base?
Changes from 18 commits
3d3d769
b85fa13
e2342f2
5c01a53
ceb91b9
b753e93
651f22b
9f1d637
42c7d00
14b4d35
210d7f3
9739d30
6422685
cd7c8a9
f2642b3
62ded33
b24b654
8b4800c
af2eec1
e3d3190
fa8e9e0
b21fef9
d0a5f26
8a15278
37a8e9d
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
# java-ladder | ||
|
||
# < controller > | ||
## 1) Controller | ||
* createPlayers() //참여자 생성기능 | ||
* createResults() //참여결과 생성기능 | ||
* createLadder() //사다리 생성기능 | ||
* createLadderResult() //사다리 결과 생성기능 | ||
* playLadderGame() //사다리 게임 실행기능 | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 자세하게 설명해주시려고 적어주신 리드미 너무 좋아요!! 개인적으로 리드미 작성에 추천드리는 방법이 있는데요 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 저도 이번 문제를 푸면서 이 부분에 대한 고민이 많았습니다 ㅜㅠ 좋은 조언감사합니다!! 앞으로는 구현한 기능에 대해 README를 작성하는 습관을 들여봐야겠어요!! README 작성을 완료했는 데 여기서 더 자세히 적어야하는 지 덜 적어야하는 지는 감이 잘 안 잡히네요 ㅎㅎㅎ하하.... There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 리드미를 남길 때, 주석을 남길때 모두 동일한데요 |
||
|
||
--- | ||
# < model > | ||
## 1) DecideResult | ||
* moveColumn() // 열부분 움직이는 기능 | ||
* moveRow() //행부분 움직이는 기능 | ||
* decidePlayerResult() //참여자 결과 결정기능 | ||
## 2) Ladder | ||
## 3) LadderRow | ||
* LadderRow() //사다리 열부분 생성기능 | ||
* chooseTrueOrFalse() //사다리 point 정하는 기능 | ||
## 4) Player | ||
* Player() //참여자 생성, 참가자이름이 5글자 초과 시 에러발생 기능 | ||
* getCertainPlayerResult //특정 사용자의 결과를 반환하는 기능 | ||
## 5) Players | ||
## 6) Results | ||
## 7) Splitter | ||
* split() //문자열 자르는 기능 | ||
|
||
--- | ||
# < view > | ||
## 1) InputView | ||
* inputPlayers() //참여할 사람이름 입력기능 | ||
* inputResults() //결과 입력기능 | ||
* inputLadderHeight() //최대 사다리 높이 입력기능 | ||
* inputPlayerToWantResult() //결과를 보고싶은 사람 입력기능 | ||
## 2) OutputView | ||
* outputPlayer() //참여자 출력기능 | ||
* outputLadderRow() //사다리행 출력기능 | ||
* outputLadder() //사다리 출력기능 | ||
* outputResults() //결과 출력기능 | ||
* outputAllPlayersResult //모든 참여자 결과 출력기능 | ||
* outputCertainPlayerResult //특정 참여자 결과 출력기능 | ||
* outputPlayerResult //참여자 결과 출력기능 |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
import controller.Controller; | ||
|
||
public class Main { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 저는 개인적으로는 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
<질문>
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 이제 프로젝트가 커졌을 때 프로젝트를 실행시키는 main 함수를 찾기가 힘든데요 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Main은 무조건 하나밖에 없으니까 왜 Main이 여러개가 나온다는 건 지 몰랐는 데 하나의 어플리케이션 안에
|
||
public static void main(String[] args) { | ||
Controller controller = new Controller(); | ||
controller.playLadderGame(); | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,80 @@ | ||
package controller; | ||
|
||
import model.ladder.Ladder; | ||
import model.ladder.LadderRow; | ||
import model.player.Player; | ||
import model.player.PlayerResults; | ||
import model.player.Players; | ||
import model.tool.Splitter; | ||
import view.InputView; | ||
import view.OutputView; | ||
|
||
import java.util.ArrayList; | ||
import java.util.Arrays; | ||
import java.util.List; | ||
import java.util.Map; | ||
|
||
|
||
public class Controller { | ||
InputView inputView = new InputView(); | ||
Splitter splitter = new Splitter(); | ||
OutputView outputView = new OutputView(); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Input VIew 쪽에 달아드린 이 클래스가 static 으로 사용하지 않는 이유를 알고 싶어요! There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 앗 딱히 이유는 없고 빼먹는 거 같습니다!! 짚어주셔서 감사합니다 :) |
||
|
||
private Players createPlayers() { | ||
String playerNamesBeforeSplit = inputView.inputPlayers(); | ||
String[] playerNames = splitter.split(playerNamesBeforeSplit); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 이 부분은 view 로 옮겨가면 좋을 것 같아요! There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 제가 전에 문자열을 나누는 기능을 <질문>private Players createPlayers() {
String playerNamesBeforeSplit = inputView.inputPlayers();
String[] playerNames = splitter.splitWithComma(playerNamesBeforeSplit);
List<Player> playersInventory = new ArrayList<>();
for (int i = 0; i < playerNames.length; i++) {
Player player = new Player(i, playerNames[i]);
playersInventory.add(player);
}
Players players = new Players(playersInventory);
return players;
} split은 그대로 놔두고 Players의 생성자가 더 많은 역할을 하도록 위의 코드를 아래의 코드로 바꿔보았는 데 혹시 이 방법은 어떠신가요..?? private Players createPlayers() {
String playerNamesBeforeSplit = inputView.inputPlayers();
String[] playerNames = splitter.splitWithComma(playerNamesBeforeSplit);
Players players = new Players(playerNames);
return players;
} There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 오 이정도로 바뀐다면 괜찮을 것 같아요!
이 부분은 진짜 취향에 따라 정말 많이 갈리는 부분이라서 그렇게 생각하신다면 그렇게 해주시면 됩니다! |
||
List<Player> playersInventory = new ArrayList<>(); | ||
for (int i = 0; i < playerNames.length; i++) { | ||
Player player = new Player(i, playerNames[i]); | ||
playersInventory.add(player); | ||
} | ||
Players players = new Players(playersInventory); | ||
return players; | ||
} | ||
|
||
private List<String> createLadderResults() { | ||
String trialResultsBeforeSplit = inputView.inputResults(); | ||
String[] trialResults = splitter.split(trialResultsBeforeSplit); | ||
List<String> ladderResults = Arrays.asList(trialResults); | ||
return ladderResults; | ||
} | ||
|
||
private Ladder createLadder(int columnSize) { | ||
List<String> ladderResults = createLadderResults(); | ||
int rowSize = inputView.inputLadderHeight(); | ||
List<LadderRow> ladderRows = new ArrayList<>(); | ||
for (int i = 0; i < rowSize; i++) { | ||
LadderRow ladderRow = new LadderRow(columnSize); | ||
ladderRows.add(ladderRow); | ||
} | ||
Ladder ladder = new Ladder(ladderRows, ladderResults); | ||
return ladder; | ||
} | ||
|
||
private PlayerResults createPlayerResults(Players players, Ladder ladder) { | ||
List<Player> playerInventory = players.getPlayerInventory(); | ||
Map<String, String> playerResultsInventory = ladder.decidePlayerResults(playerInventory); | ||
PlayerResults playerResults = new PlayerResults(playerResultsInventory); | ||
return playerResults; | ||
} | ||
|
||
private void printLadder(Players players, Ladder ladder) { | ||
List<LadderRow> ladderRows = ladder.getLadderRows(); | ||
List<String> ladderResults = ladder.getLadderResults(); | ||
List<Player> playerInventory = players.getPlayerInventory(); | ||
OutputView outputView = new OutputView(); | ||
outputView.outputLadder(playerInventory, ladderRows, ladderResults); | ||
} | ||
|
||
public void playLadderGame() { | ||
Players players = createPlayers(); | ||
Ladder ladder = createLadder(players.getPlayerInventory().size() - 1); | ||
PlayerResults playerResults = createPlayerResults(players, ladder); | ||
printLadder(players, ladder); | ||
String playerName; | ||
do { | ||
playerName = inputView.inputPlayerToWantResult(); | ||
outputView.outputPlayerResult(playerResults, playerName); | ||
} while (!playerName.equals("all")); | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,60 @@ | ||
package model.ladder; | ||
|
||
import model.player.Player; | ||
|
||
import java.util.HashMap; | ||
import java.util.List; | ||
import java.util.Map; | ||
|
||
public class Ladder { | ||
private List<LadderRow> ladderRows; | ||
private List<String> ladderResults; | ||
|
||
public Ladder(List<LadderRow> ladderRows, List<String> ladderResults) { | ||
this.ladderRows = ladderRows; | ||
this.ladderResults = ladderResults; | ||
} | ||
|
||
private LadderMove changePosition(List<Boolean> points, int columnPosition) { | ||
if (columnPosition > 0 && points.get(columnPosition - 1)) { | ||
return LadderMove.LEFT; | ||
} | ||
if (columnPosition < points.size() && points.get(columnPosition)) { | ||
return LadderMove.RIGHT; | ||
} | ||
return LadderMove.DOWN; | ||
} | ||
|
||
private int moveColumn(List<Boolean> points, int columnPosition) { | ||
LadderMove moveDirection = changePosition(points, columnPosition); | ||
return columnPosition + moveDirection.getOffset(); | ||
} | ||
|
||
private int moveRow(List<LadderRow> ladderRows, int columnPosition) { | ||
for (LadderRow ladderRow : ladderRows) { | ||
List<Boolean> points = ladderRow.getPoints(); | ||
columnPosition = moveColumn(points, columnPosition); | ||
} | ||
return columnPosition; | ||
} | ||
|
||
public Map<String, String> decidePlayerResults(List<Player> playerInventory) { | ||
Map<String, String> playerResultsInventory = new HashMap<>(); | ||
for (Player player : playerInventory) { | ||
int playerPosition = player.getPosition(); | ||
int columnPosition = moveRow(ladderRows, playerPosition); | ||
String playerName = player.getName(); | ||
String playerResult = ladderResults.get(columnPosition); | ||
playerResultsInventory.put(playerName, playerResult); | ||
} | ||
return playerResultsInventory; | ||
} | ||
|
||
public List<LadderRow> getLadderRows() { | ||
return ladderRows; | ||
} | ||
|
||
public List<String> getLadderResults() { | ||
return ladderResults; | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
package model.ladder; | ||
|
||
public enum LadderMove { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 이 부분까지 enum 으로 두기 쉽지 않았을텐데 분리하려고 열심히 하신 것이 보여서 되게 좋네요! There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 감사합니다!! |
||
RIGHT(1), | ||
LEFT(-1), | ||
DOWN(0); | ||
|
||
private final int offset; | ||
|
||
LadderMove(int offset) { | ||
this.offset = offset; | ||
} | ||
|
||
public int getOffset() { | ||
return offset; | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,16 @@ | ||
package model.ladder; | ||
|
||
public enum LadderPoint { | ||
CONNECTED(true), | ||
DISCONNECTED(false); | ||
|
||
private final Boolean isConnected; | ||
|
||
LadderPoint(Boolean isConnected) { | ||
this.isConnected = isConnected; | ||
} | ||
|
||
public Boolean getConnected() { | ||
return isConnected; | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,31 @@ | ||
package model.ladder; | ||
|
||
import java.util.ArrayList; | ||
import java.util.List; | ||
|
||
public class LadderRow { | ||
private List<Boolean> points = new ArrayList<>(); | ||
|
||
public LadderRow(int columnSize) { | ||
for (int columnPosition = 0; columnPosition < columnSize; columnPosition++) { | ||
boolean randomBoolean = chooseLadderPoint(columnPosition); | ||
this.points.add(columnPosition, randomBoolean); | ||
} | ||
} | ||
|
||
private LadderPoint randomTrueOrFalse() { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 이 메소드의 경우에 randomTrueOrFalse 라는 네이밍을 봤을 때는 뭔가 boolean 타입을 반환해야 할 것 같은데 어떻게 생각하시나요? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 앗! 생각 못 해봤는 데 |
||
if (Math.random() < 0.5) return LadderPoint.CONNECTED; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. https://morethantoday.tistory.com/94 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Math.random()을 실무에서는 쓰지 않는다니... 몰랐던 사실이군요! private LadderPoint randomTrueOrFalse() {
if (ThreadLocalRandom.current().nextDouble() < 0.5) return LadderPoint.CONNECTED;
return LadderPoint.DISCONNECTED;
} There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 넵 좋아요! 👍 |
||
return LadderPoint.DISCONNECTED; | ||
} | ||
|
||
public boolean chooseLadderPoint(int columnPosition) { | ||
if (columnPosition > 0 && points.get(columnPosition - 1)) | ||
return LadderPoint.DISCONNECTED.getConnected(); | ||
return randomTrueOrFalse().getConnected(); | ||
|
||
} | ||
|
||
public List<Boolean> getPoints() { | ||
return points; | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,23 @@ | ||
package model.player; | ||
|
||
public class Player { | ||
private static final int NAME_LENGTH_LIMIT = 5; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 자바 컨벤션 상으로 static 변수와 일반 변수는 1줄을 띄워야 할 것 같아요! There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 앗 static 변수와 일반 변수는 1줄을 띄어야 하는 군요! 수정하겠습니다!! |
||
private int position; | ||
private String name; | ||
|
||
public Player(int position, String name) { | ||
if (name.length() > NAME_LENGTH_LIMIT) { | ||
throw new IllegalArgumentException("참가자 이름이 " + NAME_LENGTH_LIMIT + "자 초과입니다."); | ||
} | ||
this.position = position; | ||
this.name = name; | ||
} | ||
|
||
public int getPosition() { | ||
return position; | ||
} | ||
|
||
public String getName() { | ||
return name; | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,19 @@ | ||
package model.player; | ||
|
||
import java.util.Map; | ||
|
||
public class PlayerResults { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 바로 전에 말씀드린 Players 와는 반대로 이 클래스는 충분히 있어도 된다고 생각하는 편이긴 한데요 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 이번 기회를 통해 Map과 DTO의 차이점에 대해 알아보았습니다!
→ 결론: 장단점을 비교해놓고 보니 확실히 프로그램이 커질수록 정보관리에는 DTO를 쓰는 게 더 적합하다는 생각이 듭니다!! |
||
private Map<String, String> PlayerResultsInventory; | ||
|
||
public PlayerResults(Map<String, String> playerResultsInventory) { | ||
PlayerResultsInventory = playerResultsInventory; | ||
} | ||
|
||
public String getPlayerResult(String playerName) { | ||
return PlayerResultsInventory.get(playerName); | ||
} | ||
|
||
public Map<String, String> getPlayerResultsInventory() { | ||
return PlayerResultsInventory; | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,15 @@ | ||
package model.player; | ||
|
||
import java.util.List; | ||
|
||
public class Players { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 일급 컬렉션을 지키려고 노력하신 부분이 보여서 고생 많으셨다는 생각이 드네요 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. < 질문 >컨트롤러의 역할을 줄이기 위해 아래와 같이 Player객체 생성을 public Players(String [] playerNames){
for (int i = 0; i < playerNames.length; i++) {
Player player = new Player(i, playerNames[i]);
playerInventory.add(player);
}
} There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 만약 그렇게 역할이 딱히 없다면 list 형태로 들고다녀도 저는 좋다고 생각합니다! |
||
private List<Player> playerInventory; | ||
|
||
public Players(List<Player> playerInventory) { | ||
this.playerInventory = playerInventory; | ||
} | ||
|
||
public List<Player> getPlayerInventory() { | ||
return playerInventory; | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,13 @@ | ||
package model.tool; | ||
|
||
public class Splitter { | ||
final static private String SPLIT_SIGN = ","; | ||
|
||
public String[] split(String beforeSplit) { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 다른분 리뷰에서 남겼던 내용인데요 이런 형태로 바뀌게 되면 쓰는 입장에서는 조금 더 생각하지 않고 쓸 수 있을 것 같아요 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
|
||
String[] afterSplit = beforeSplit.split(SPLIT_SIGN); | ||
for (int i = 0; i < afterSplit.length; i++) { | ||
afterSplit[i] = afterSplit[i].trim(); | ||
} | ||
return afterSplit; | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,26 @@ | ||
package view; | ||
|
||
import java.util.Scanner; | ||
|
||
public class InputView { | ||
Scanner scanner = new Scanner(System.in); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 다른 부분의 구현을 정말 잘 해주신 것 같아서 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 딱히 이유는 없습니다 ㅜㅠ 현재 스캐너와 <질문>static을 붙이는 이유가 "이 값은 객체마다의 특징을 나타내는 값이 아니다"라는 특징을 명시해주기 위해서 인가요? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 보통 스태틱으로 할당되는 메모리는 신경쓸 필요가 없어요 (map 에 10만개쯤 넣는 순간부터 고민해도 충분합니다) 스태틱을 쓰면 가장 간단하게는 생성자가 간단해지잖아요? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. staic이라는 게 생각보다 메모리를 많이 잡아먹진 않군요 :) 몰랐던 지식인 데 알려주셔서 감사합니다! 생성자가 간단해진다는 생각은 못 해봤어요!! 생각해보지 못 한 관점이네요. private String name = "아무개"; There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 만약 그렇게 된다면 큰 차이는 없을 것 같아요! There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
|
||
public String inputPlayers(){ | ||
System.out.println("참여할 사람 이름을 입력하세요. (이름은 쉼표(,)로 구분하세요)"); | ||
return scanner.nextLine(); | ||
} | ||
|
||
public String inputResults(){ | ||
System.out.println("\n"+"실행 결과를 입력하세요. (결과는 쉼표(,)로 구분하세요)"); | ||
return scanner.nextLine(); | ||
} | ||
|
||
public Integer inputLadderHeight(){ | ||
System.out.println("\n"+"최대 사다리 높이는 몇 개인가요?"); | ||
return Integer.parseInt(scanner.nextLine()); | ||
} | ||
|
||
public String inputPlayerToWantResult(){ | ||
System.out.println("\n"+"결과를 보고 싶은 사람은?"); | ||
return scanner.nextLine(); | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
헉 리드미를 작성해주셔서 한 눈에 보기가 편하네요!