From 43952e69fac7f10ba7ee35eb29311522cd1b9006 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 17:14:12 +0900 Subject: [PATCH 01/30] =?UTF-8?q?docs:=20=EC=9A=94=EA=B5=AC=EC=82=AC?= =?UTF-8?q?=ED=95=AD=20=EB=AA=A8=EB=8D=B8=EB=A7=81=20=EB=B0=8F=20=EC=A0=95?= =?UTF-8?q?=EC=9D=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- SOLUTION.md | 202 ++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 202 insertions(+) create mode 100644 SOLUTION.md diff --git a/SOLUTION.md b/SOLUTION.md new file mode 100644 index 000000000..8cb45df0e --- /dev/null +++ b/SOLUTION.md @@ -0,0 +1,202 @@ +# 페어 매칭 관리 모델링 + +## 용어 정리 + +### 크루 +| 용어 | 설명 | +|-------------|----------------| +| Crew | 우테코에서 학습하는 사람들 | +| Crew Name | 크루 이름 | +| Crew Course | 크루가 참여하는 분야 | + +### 미션 +| 용어 | 설명 | +|---------|-----------------------| +| Mission | 학습 레벨마다 구분되어 존재하는 미션들 | + +### 레벨 +| 용어 | 설명 | +|---------|------------------------| +| Level | 우테코 학습 단계를 구분한 것 1~5단계 존재 | +| Mission | 각 단계마다 미션이 존재 | + +### 분야 +| 용어 | 설명 | +|--------|----------------------------| +| Course | 크루가 참가하는 분야로 백엔드 프론트엔드가 있음 | + + +## 개발 요구사항 + +### 페어 매칭 기능 +- 페어 매칭 조건 + - [ ] 미션을 함께 수행할 페어를 두명씩 매칭한다. + - [ ] 페어 매칭 대상이 홀수인 경우 한 페어는 3인으로 구성한다. + - [ ] 같은 레벨에서 이미 페어를 맺은 크루와는 다시 페어로 매칭될 수 없다. + +- 페어 매칭 구현 방법 + - [ ] 크루들의 이름 목록을 List 형태로 준비한다. + - [ ] 크루 목록의 순서를 랜덤으로 섞는다. 이 때 `camp.nextstep.edu.missionutils.Randoms`의 shuffle 메서드를 활용해야 한다. + - [ ] 랜덤으로 섞인 페어 목록에서 페어 매칭을 할 때 앞에서부터 순서대로 두명씩 페어를 맺는다. + - [ ] 홀수인 경우 마지막 남은 크루는 마지막 페어에 포함시킨다. + - [ ] 같은 레벨에서 이미 페어로 만난적이 있는 크루끼리 다시 페어로 매칭 된다면 크루 목록의 순서를 다시 랜덤으로 섞어서 매칭을 시도한다. + - [ ] 3회 시도까지 매칭이 되지 않거나 매칭을 할 수 있는 경우의 수가 없으면 에러 메시지를 출력한다. + +### 파일 입출력 +- [ ] 페어 매칭에 필요한 크루들의 이름을 파일 입출력을 통해 불러온다. +- [ ] `src/main/resources/backend-crew.md`과 `src/main/resources/frontend-crew.md` 파일을 이용한다. +- [ ] 두 파일의 내용은 수정이 가능하다. 수정 시 크루들의 이름은 중복될 수 없다. +- [ ] 파일 입출력 방법은 `자바 파일 읽기`나 `자바 파일 입출력`과 같은 키워드로 구글링해서 찾을 수 있다. + +### 에러 처리 +- [ ] 사용자가 잘못된 값을 입력할 경우 `IllegalArgumentException`를 발생시키고, `[ERROR]`로 시작하는 에러 메시지를 출력 후 해당 부분부터 다시 입력을 받는다. +- [ ] 아래의 프로그래밍 실행 결과 예시와 동일하게 입력과 출력이 이루어져야 한다. + +### 기능 선택 +- [ ] 프로그램을 시작하면 기능의 종류를 출력하고 그 중 하나의 입력을 받는다. + +``` +기능을 선택하세요. +1. 페어 매칭 +2. 페어 조회 +3. 페어 초기화 +Q. 종료 +``` + +### 페어 매칭 +- [ ] 과정와 미션을 출력하고 매칭하고자 하는 과정, 레벨, 미션을 입력 받는다. + +``` +############################################# +과정: 백엔드 | 프론트엔드 +미션: + - 레벨1: 자동차경주 | 로또 | 숫자야구게임 + - 레벨2: 장바구니 | 결제 | 지하철노선도 + - 레벨3: + - 레벨4: 성능개선 | 배포 + - 레벨5: +############################################ +과정, 레벨, 미션을 선택하세요. +ex) 백엔드, 레벨1, 자동차경주 +``` + +- [ ] 매칭이 정상적으로 수행되면 결과가 출력된다. +- [ ] 출력되는 페어의 순서는 `camp.nextstep.edu.missionutils.Randoms`의 shuffle 메서드의 결과 순서로 정렬한다. + +### 프로그래밍 실행 결과 예시 + +``` +기능을 선택하세요. +1. 페어 매칭 +2. 페어 조회 +3. 페어 초기화 +Q. 종료 +1 + +############################################# +과정: 백엔드 | 프론트엔드 +미션: + - 레벨1: 자동차경주 | 로또 | 숫자야구게임 + - 레벨2: 장바구니 | 결제 | 지하철노선도 + - 레벨3: + - 레벨4: 성능개선 | 배포 + - 레벨5: +############################################ +과정, 레벨, 미션을 선택하세요. +ex) 백엔드, 레벨1, 자동차경주 +프론트엔드, 레벨1, 자동차경주 + +페어 매칭 결과입니다. +다비 : 신디 +쉐리 : 덴버 +제키 : 로드 +라라 : 윌터 +니콜 : 이브 +린다 : 시저 +보노 : 제시 : 제키 + +기능을 선택하세요. +1. 페어 매칭 +2. 페어 조회 +3. 페어 초기화 +Q. 종료 +1 + +############################################# +과정: 백엔드 | 프론트엔드 +미션: + - 레벨1: 자동차경주 | 로또 | 숫자야구게임 + - 레벨2: 장바구니 | 결제 | 지하철노선도 + - 레벨3: + - 레벨4: 성능개선 | 배포 + - 레벨5: +############################################ +과정, 레벨, 미션을 선택하세요. +ex) 백엔드, 레벨1, 자동차경주 +프론트엔드, 레벨1, 자동차경주 + +매칭 정보가 있습니다. 다시 매칭하시겠습니까? +네 | 아니오 +아니오 + +과정, 레벨, 미션을 선택하세요. +ex) 백엔드, 레벨1, 자동차경주 +프론트엔드, 레벨1, 자동차경주 +매칭 정보가 있습니다. 다시 매칭하시겠습니까? +네 | 아니오 +네 + +페어 매칭 결과입니다. +이브 : 윌터 +보노 : 제키 +신디 : 로드 +제시 : 린다 +시저 : 라라 +니콜 : 다비 +리사 : 덴버 : 제키 + +기능을 선택하세요. +1. 페어 매칭 +2. 페어 조회 +3. 페어 초기화 +Q. 종료 +2 + +############################################# +과정: 백엔드 | 프론트엔드 +미션: + - 레벨1: 자동차경주 | 로또 | 숫자야구게임 + - 레벨2: 장바구니 | 결제 | 지하철노선도 + - 레벨3: + - 레벨4: 성능개선 | 배포 + - 레벨5: +############################################ +과정, 레벨, 미션을 선택하세요. +ex) 백엔드, 레벨1, 자동차경주 +프론트엔드, 레벨1, 자동차경주 + +페어 매칭 결과입니다. +이브 : 윌터 +보노 : 제키 +신디 : 로드 +제시 : 린다 +시저 : 라라 +니콜 : 다비 +리사 : 덴버 : 제키 + +기능을 선택하세요. +1. 페어 매칭 +2. 페어 조회 +3. 페어 초기화 +Q. 종료 +3 + +초기화 되었습니다. + +기능을 선택하세요. +1. 페어 매칭 +2. 페어 조회 +3. 페어 초기화 +Q. 종료 +Q +``` From 425c279fc80a3fe272b1fdcc92240e09e561e06c Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 17:15:55 +0900 Subject: [PATCH 02/30] =?UTF-8?q?feat:=20=EB=A0=88=EB=B2=A8=EA=B3=BC=20?= =?UTF-8?q?=EA=B3=BC=EC=A0=95=20enum=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/pairmatching/model/Course.java | 14 ++++++++++++++ src/main/java/pairmatching/model/Level.java | 17 +++++++++++++++++ 2 files changed, 31 insertions(+) create mode 100644 src/main/java/pairmatching/model/Course.java create mode 100644 src/main/java/pairmatching/model/Level.java diff --git a/src/main/java/pairmatching/model/Course.java b/src/main/java/pairmatching/model/Course.java new file mode 100644 index 000000000..14c785ea3 --- /dev/null +++ b/src/main/java/pairmatching/model/Course.java @@ -0,0 +1,14 @@ +package pairmatching.model; + +public enum Course { + + BACKEND("백엔드"), + FRONTEND("프론트엔드"); + + private String name; + + Course(String name) { + this.name = name; + } + +} diff --git a/src/main/java/pairmatching/model/Level.java b/src/main/java/pairmatching/model/Level.java new file mode 100644 index 000000000..0bd21875a --- /dev/null +++ b/src/main/java/pairmatching/model/Level.java @@ -0,0 +1,17 @@ +package pairmatching.model; + +public enum Level { + + LEVEL1("레벨1"), + LEVEL2("레벨2"), + LEVEL3("레벨3"), + LEVEL4("레벨4"), + LEVEL5("레벨5"); + + private String name; + + Level(String name) { + this.name = name; + } + +} From 8f1a962fa68b93f914d9bc71f976cb44c5d5cd0c Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 17:22:47 +0900 Subject: [PATCH 03/30] =?UTF-8?q?feat:=20=ED=8C=8C=EC=9D=BC=20=EC=9E=85?= =?UTF-8?q?=EB=A0=A5=20=EA=B8=B0=EB=8A=A5=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../service/FileReaderService.java | 30 +++++++++++++++++++ 1 file changed, 30 insertions(+) create mode 100644 src/main/java/pairmatching/service/FileReaderService.java diff --git a/src/main/java/pairmatching/service/FileReaderService.java b/src/main/java/pairmatching/service/FileReaderService.java new file mode 100644 index 000000000..ddd69acaa --- /dev/null +++ b/src/main/java/pairmatching/service/FileReaderService.java @@ -0,0 +1,30 @@ +package pairmatching.service; + +import java.io.BufferedReader; +import java.io.FileReader; +import java.io.IOException; +import java.util.List; +import java.util.stream.Collectors; + +public class FileReaderService { + + private static final String BACKEND_CREW_DIR = "src/main/resources/backend-crew.md"; + private static final String FRONTEND_CREW_DIR = "src/main/resources/frontend-crew.md"; + + public static List readBackendCrews() { + return readFile(BACKEND_CREW_DIR); + } + + public static List readFrontendCrews() { + return readFile(FRONTEND_CREW_DIR); + } + + private static List readFile(String filePath) { + try (BufferedReader bufferedReader = new BufferedReader(new FileReader(filePath))) { + return bufferedReader.lines().collect(Collectors.toList()); + } catch (IOException e) { + throw new IllegalArgumentException("읽을 수 없는 파일 입니다."); + } + } + +} From 6a7478dc1ae6846011629d742f72c493dec19dc1 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 17:23:00 +0900 Subject: [PATCH 04/30] =?UTF-8?q?feat:=20=ED=81=AC=EB=A3=A8=20=ED=81=B4?= =?UTF-8?q?=EB=9E=98=EC=8A=A4=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/pairmatching/model/Crew.java | 13 +++++++++++++ 1 file changed, 13 insertions(+) create mode 100644 src/main/java/pairmatching/model/Crew.java diff --git a/src/main/java/pairmatching/model/Crew.java b/src/main/java/pairmatching/model/Crew.java new file mode 100644 index 000000000..4d776ad2a --- /dev/null +++ b/src/main/java/pairmatching/model/Crew.java @@ -0,0 +1,13 @@ +package pairmatching.model; + +public class Crew { + + private final Course course; + private final String name; + + public Crew(Course course, String name) { + this.course = course; + this.name = name; + } + +} From ccd4c4f971532dcc99c61e0f9fe1e2c3b01c2292 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 17:27:14 +0900 Subject: [PATCH 05/30] =?UTF-8?q?feat:=20=EA=B8=B0=EB=B3=B8=20=ED=81=B4?= =?UTF-8?q?=EB=9E=98=EC=8A=A4=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/pairmatching/Application.java | 9 ++++- .../java/pairmatching/config/AppConfig.java | 37 +++++++++++++++++++ .../pairmatching/controller/Controller.java | 20 ++++++++++ .../java/pairmatching/view/InputView.java | 4 ++ .../java/pairmatching/view/OutputView.java | 4 ++ 5 files changed, 73 insertions(+), 1 deletion(-) create mode 100644 src/main/java/pairmatching/config/AppConfig.java create mode 100644 src/main/java/pairmatching/controller/Controller.java create mode 100644 src/main/java/pairmatching/view/InputView.java create mode 100644 src/main/java/pairmatching/view/OutputView.java diff --git a/src/main/java/pairmatching/Application.java b/src/main/java/pairmatching/Application.java index 6f56e741c..8f9c97441 100644 --- a/src/main/java/pairmatching/Application.java +++ b/src/main/java/pairmatching/Application.java @@ -1,7 +1,14 @@ package pairmatching; +import pairmatching.config.AppConfig; +import pairmatching.controller.Controller; + public class Application { + public static void main(String[] args) { - // TODO 구현 진행 + AppConfig appConfig = new AppConfig(); + Controller controller = appConfig.controller(); + controller.run(); } + } diff --git a/src/main/java/pairmatching/config/AppConfig.java b/src/main/java/pairmatching/config/AppConfig.java new file mode 100644 index 000000000..38910c85a --- /dev/null +++ b/src/main/java/pairmatching/config/AppConfig.java @@ -0,0 +1,37 @@ +package pairmatching.config; + +import pairmatching.controller.Controller; +import pairmatching.view.InputView; +import pairmatching.view.OutputView; + +public class AppConfig { + + private InputView inputView; + private OutputView outputView; + private Controller controller; + + public AppConfig() { + } + + private InputView inputView() { + if (inputView == null) { + return inputView = new InputView(); + } + return inputView; + } + + private OutputView outputView() { + if (outputView == null) { + return outputView = new OutputView(); + } + return outputView; + } + + public Controller controller() { + if (controller == null) { + return controller = new Controller(inputView(), outputView()); + } + return controller; + } + +} diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java new file mode 100644 index 000000000..d4ef94902 --- /dev/null +++ b/src/main/java/pairmatching/controller/Controller.java @@ -0,0 +1,20 @@ +package pairmatching.controller; + +import pairmatching.view.InputView; +import pairmatching.view.OutputView; + +public class Controller { + + private final InputView inputView; + private final OutputView outputView; + + public Controller(InputView inputView, OutputView outputView) { + this.inputView = inputView; + this.outputView = outputView; + } + + public void run() { + + } + +} diff --git a/src/main/java/pairmatching/view/InputView.java b/src/main/java/pairmatching/view/InputView.java new file mode 100644 index 000000000..c042bfc93 --- /dev/null +++ b/src/main/java/pairmatching/view/InputView.java @@ -0,0 +1,4 @@ +package pairmatching.view; + +public class InputView { +} diff --git a/src/main/java/pairmatching/view/OutputView.java b/src/main/java/pairmatching/view/OutputView.java new file mode 100644 index 000000000..5a43c742c --- /dev/null +++ b/src/main/java/pairmatching/view/OutputView.java @@ -0,0 +1,4 @@ +package pairmatching.view; + +public class OutputView { +} From c2cedcee81cc5a4de61feb12139d54ab647a7255 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 17:43:03 +0900 Subject: [PATCH 06/30] =?UTF-8?q?feat:=20=ED=81=AC=EB=A3=A8=20=EA=B0=9D?= =?UTF-8?q?=EC=B2=B4=20=EC=83=9D=EC=84=B1=20=EA=B8=B0=EB=8A=A5=20=EC=B6=94?= =?UTF-8?q?=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pairmatching/controller/Controller.java | 14 ++++++++++++ src/main/java/pairmatching/model/Crew.java | 6 ++++- src/main/java/pairmatching/model/Crews.java | 22 +++++++++++++++++++ .../service/FileReaderService.java | 14 +++--------- 4 files changed, 44 insertions(+), 12 deletions(-) create mode 100644 src/main/java/pairmatching/model/Crews.java diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index d4ef94902..8b4da83b9 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -1,5 +1,12 @@ package pairmatching.controller; +import static pairmatching.service.FileReaderService.BACKEND_CREW_DIR; +import static pairmatching.service.FileReaderService.FRONTEND_CREW_DIR; + +import java.util.List; +import pairmatching.model.Course; +import pairmatching.model.Crews; +import pairmatching.service.FileReaderService; import pairmatching.view.InputView; import pairmatching.view.OutputView; @@ -14,7 +21,14 @@ public Controller(InputView inputView, OutputView outputView) { } public void run() { + Crews backendCrews = readCrews(BACKEND_CREW_DIR, Course.BACKEND); + Crews frontendCrews = readCrews(FRONTEND_CREW_DIR, Course.FRONTEND); + + } + private Crews readCrews(String dir, Course course) { + List names = FileReaderService.readFile(dir); + return Crews.from(names, course); } } diff --git a/src/main/java/pairmatching/model/Crew.java b/src/main/java/pairmatching/model/Crew.java index 4d776ad2a..637c80ecb 100644 --- a/src/main/java/pairmatching/model/Crew.java +++ b/src/main/java/pairmatching/model/Crew.java @@ -5,9 +5,13 @@ public class Crew { private final Course course; private final String name; - public Crew(Course course, String name) { + private Crew(Course course, String name) { this.course = course; this.name = name; } + public static Crew from(Course course, String name) { + return new Crew(course, name); + } + } diff --git a/src/main/java/pairmatching/model/Crews.java b/src/main/java/pairmatching/model/Crews.java new file mode 100644 index 000000000..4532da356 --- /dev/null +++ b/src/main/java/pairmatching/model/Crews.java @@ -0,0 +1,22 @@ +package pairmatching.model; + +import java.util.ArrayList; +import java.util.List; + +public class Crews { + + private final List crews; + + private Crews(List crews) { + this.crews = crews; + } + + public static Crews from(List names, Course course) { + List crews = new ArrayList<>(); + for (String name : names) { + crews.add(Crew.from(course, name)); + } + return new Crews(crews); + } + +} diff --git a/src/main/java/pairmatching/service/FileReaderService.java b/src/main/java/pairmatching/service/FileReaderService.java index ddd69acaa..70bd9bf2c 100644 --- a/src/main/java/pairmatching/service/FileReaderService.java +++ b/src/main/java/pairmatching/service/FileReaderService.java @@ -8,18 +8,10 @@ public class FileReaderService { - private static final String BACKEND_CREW_DIR = "src/main/resources/backend-crew.md"; - private static final String FRONTEND_CREW_DIR = "src/main/resources/frontend-crew.md"; + public static final String BACKEND_CREW_DIR = "src/main/resources/backend-crew.md"; + public static final String FRONTEND_CREW_DIR = "src/main/resources/frontend-crew.md"; - public static List readBackendCrews() { - return readFile(BACKEND_CREW_DIR); - } - - public static List readFrontendCrews() { - return readFile(FRONTEND_CREW_DIR); - } - - private static List readFile(String filePath) { + public static List readFile(String filePath) { try (BufferedReader bufferedReader = new BufferedReader(new FileReader(filePath))) { return bufferedReader.lines().collect(Collectors.toList()); } catch (IOException e) { From 6d4ab31b738d53f387d8e3d6e2c738b40e9a387b Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 17:57:54 +0900 Subject: [PATCH 07/30] =?UTF-8?q?feat:=20=EB=AF=B8=EC=85=98=20enum=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/pairmatching/model/Course.java | 2 +- src/main/java/pairmatching/model/Level.java | 2 +- src/main/java/pairmatching/model/Mission.java | 22 +++++++++++++++++++ 3 files changed, 24 insertions(+), 2 deletions(-) create mode 100644 src/main/java/pairmatching/model/Mission.java diff --git a/src/main/java/pairmatching/model/Course.java b/src/main/java/pairmatching/model/Course.java index 14c785ea3..96bd878b0 100644 --- a/src/main/java/pairmatching/model/Course.java +++ b/src/main/java/pairmatching/model/Course.java @@ -5,7 +5,7 @@ public enum Course { BACKEND("백엔드"), FRONTEND("프론트엔드"); - private String name; + private final String name; Course(String name) { this.name = name; diff --git a/src/main/java/pairmatching/model/Level.java b/src/main/java/pairmatching/model/Level.java index 0bd21875a..77a0182c0 100644 --- a/src/main/java/pairmatching/model/Level.java +++ b/src/main/java/pairmatching/model/Level.java @@ -8,7 +8,7 @@ public enum Level { LEVEL4("레벨4"), LEVEL5("레벨5"); - private String name; + private final String name; Level(String name) { this.name = name; diff --git a/src/main/java/pairmatching/model/Mission.java b/src/main/java/pairmatching/model/Mission.java new file mode 100644 index 000000000..2774073ee --- /dev/null +++ b/src/main/java/pairmatching/model/Mission.java @@ -0,0 +1,22 @@ +package pairmatching.model; + +public enum Mission { + + RACING_CAR("자동차경주"), + LOTTO("로또"), + NUMBER_BASEBALL("숫자야구게임"), + + SHOPPING_CART("장바구니"), + PAYMENT("결제"), + SUBWAY("지하철노선도"), + + IMPROVEMENT("성능개선"), + DEPLOY("배포"); + + private final String name; + + Mission(String name) { + this.name = name; + } + +} From 0b7875ac86524ec26b9f7b653f6ef9db1c634d8c Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 18:01:06 +0900 Subject: [PATCH 08/30] =?UTF-8?q?feat:=20=EB=AF=B8=EC=85=98=EC=9D=98=20?= =?UTF-8?q?=EB=A0=88=EB=B2=A8=EB=B3=84=20=EC=B6=9C=EB=A0=A5=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/pairmatching/model/Mission.java | 20 +++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/src/main/java/pairmatching/model/Mission.java b/src/main/java/pairmatching/model/Mission.java index 2774073ee..32b77136c 100644 --- a/src/main/java/pairmatching/model/Mission.java +++ b/src/main/java/pairmatching/model/Mission.java @@ -19,4 +19,24 @@ public enum Mission { this.name = name; } + public static String level1() { + return RACING_CAR.name + " | " + LOTTO.name + " | " + NUMBER_BASEBALL; + } + + public static String level2() { + return SHOPPING_CART.name + " | " + PAYMENT.name + " | " + SUBWAY; + } + + public static String level3() { + return ""; + } + + public static String level4() { + return IMPROVEMENT.name + " | " + DEPLOY.name; + } + + public static String level5() { + return ""; + } + } From cfb23029b34328cc48c1ec0e777346fd18d001aa Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 18:04:18 +0900 Subject: [PATCH 09/30] =?UTF-8?q?feat:=20=EA=B3=BC=EC=A0=95,=20=EB=A0=88?= =?UTF-8?q?=EB=B2=A8,=20=EB=AF=B8=EC=85=98=EC=9D=84=20=EC=9E=85=EB=A0=A5?= =?UTF-8?q?=EB=B0=9B=EB=8A=94=20=EA=B8=B0=EB=8A=A5=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pairmatching/controller/Controller.java | 16 +++++++++ .../java/pairmatching/view/InputView.java | 34 +++++++++++++++++++ 2 files changed, 50 insertions(+) diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index 8b4da83b9..8d7e4e61e 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -24,6 +24,18 @@ public void run() { Crews backendCrews = readCrews(BACKEND_CREW_DIR, Course.BACKEND); Crews frontendCrews = readCrews(FRONTEND_CREW_DIR, Course.FRONTEND); + String function; + while (!"Q".equals(function = inputView.readFunctionSelect())) { + if ("1".equals(function)) { + pairMatching(backendCrews, frontendCrews); + } + if ("2".equals(function)) { + return; + } + if ("3".equals(function)) { + return; + } + } } private Crews readCrews(String dir, Course course) { @@ -31,4 +43,8 @@ private Crews readCrews(String dir, Course course) { return Crews.from(names, course); } + private void pairMatching(Crews backendCrews, Crews frontendCrews) { + inputView.readPairMatchingInformation(); + } + } diff --git a/src/main/java/pairmatching/view/InputView.java b/src/main/java/pairmatching/view/InputView.java index c042bfc93..cea0adce7 100644 --- a/src/main/java/pairmatching/view/InputView.java +++ b/src/main/java/pairmatching/view/InputView.java @@ -1,4 +1,38 @@ package pairmatching.view; +import camp.nextstep.edu.missionutils.Console; +import pairmatching.model.Course; +import pairmatching.model.Mission; + public class InputView { + + public String readFunctionSelect() { + System.out.println("기능을 선택하세요."); + System.out.println("1. 페어 매칭"); + System.out.println("2. 페어 조회"); + System.out.println("3. 페어 초기화"); + System.out.println("Q. 종료"); + return Console.readLine(); + } + + public String readPairMatchingInformation() { + System.out.println(); + printWooWaInformation(); + System.out.println("과정, 레벨, 미션을 선택하세요."); + System.out.println("ex) 백엔드, 레벨1, 자동차경주"); + return Console.readLine(); + } + + private void printWooWaInformation() { + System.out.println("#############################################"); + System.out.println("과정: " + Course.BACKEND.name() + " | " + Course.FRONTEND.name()); + System.out.println("미션: "); + System.out.println(Mission.level1()); + System.out.println(Mission.level2()); + System.out.println(Mission.level3()); + System.out.println(Mission.level4()); + System.out.println(Mission.level5()); + System.out.println("#############################################"); + } + } From c0ba8be84ca577da4d65498d390f5d461e77512c Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 18:50:47 +0900 Subject: [PATCH 10/30] =?UTF-8?q?feat:=20=ED=8E=98=EC=96=B4=20=EB=A7=A4?= =?UTF-8?q?=EC=B9=AD=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pairmatching/controller/Controller.java | 21 ++++++++-- .../pairmatching/dto/PairMatchingDto.java | 41 +++++++++++++++++++ .../dto/PairMatchingResultDto.java | 17 ++++++++ src/main/java/pairmatching/model/Crew.java | 4 ++ src/main/java/pairmatching/model/Crews.java | 29 +++++++++++++ .../pairmatching/service/InputParser.java | 15 +++++++ 6 files changed, 124 insertions(+), 3 deletions(-) create mode 100644 src/main/java/pairmatching/dto/PairMatchingDto.java create mode 100644 src/main/java/pairmatching/dto/PairMatchingResultDto.java create mode 100644 src/main/java/pairmatching/service/InputParser.java diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index 8d7e4e61e..041d4f473 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -3,10 +3,15 @@ import static pairmatching.service.FileReaderService.BACKEND_CREW_DIR; import static pairmatching.service.FileReaderService.FRONTEND_CREW_DIR; +import java.util.HashMap; import java.util.List; +import java.util.Map; +import pairmatching.dto.PairMatchingDto; +import pairmatching.dto.PairMatchingResultDto; import pairmatching.model.Course; import pairmatching.model.Crews; import pairmatching.service.FileReaderService; +import pairmatching.service.InputParser; import pairmatching.view.InputView; import pairmatching.view.OutputView; @@ -24,10 +29,11 @@ public void run() { Crews backendCrews = readCrews(BACKEND_CREW_DIR, Course.BACKEND); Crews frontendCrews = readCrews(FRONTEND_CREW_DIR, Course.FRONTEND); + Map pairMatchingResults = new HashMap<>(); String function; while (!"Q".equals(function = inputView.readFunctionSelect())) { if ("1".equals(function)) { - pairMatching(backendCrews, frontendCrews); + matchPairs(pairMatchingResults, backendCrews, frontendCrews); } if ("2".equals(function)) { return; @@ -43,8 +49,17 @@ private Crews readCrews(String dir, Course course) { return Crews.from(names, course); } - private void pairMatching(Crews backendCrews, Crews frontendCrews) { - inputView.readPairMatchingInformation(); + private void matchPairs(Map pairMatchingResults, + Crews backendCrews, Crews frontendCrews) { + PairMatchingDto pairMatchingDto = InputParser.parsePairMatchingInformation( + inputView.readPairMatchingInformation()); + + if (pairMatchingDto.isBackend()) { + pairMatchingResults.put(pairMatchingDto, backendCrews.pairMatching()); + return; + } + pairMatchingResults.put(pairMatchingDto, frontendCrews.pairMatching()); + //validate } } diff --git a/src/main/java/pairmatching/dto/PairMatchingDto.java b/src/main/java/pairmatching/dto/PairMatchingDto.java new file mode 100644 index 000000000..8584df1e5 --- /dev/null +++ b/src/main/java/pairmatching/dto/PairMatchingDto.java @@ -0,0 +1,41 @@ +package pairmatching.dto; + +import java.util.Objects; +import pairmatching.model.Course; + +public class PairMatchingDto { + + private final String course; + private final String level; + private final String mission; + + private PairMatchingDto(String course, String level, String mission) { + this.course = course; + this.level = level; + this.mission = mission; + } + + public static PairMatchingDto of(String course, String level, String mission) { + return new PairMatchingDto(course, level, mission); + } + + public boolean isBackend() { + return Course.BACKEND.name().equals(course); + } + + @Override + public boolean equals(Object o) { + if (o == null || getClass() != o.getClass()) { + return false; + } + PairMatchingDto that = (PairMatchingDto) o; + return Objects.equals(course, that.course) && Objects.equals(level, that.level) + && Objects.equals(mission, that.mission); + } + + @Override + public int hashCode() { + return Objects.hash(course, level, mission); + } + +} diff --git a/src/main/java/pairmatching/dto/PairMatchingResultDto.java b/src/main/java/pairmatching/dto/PairMatchingResultDto.java new file mode 100644 index 000000000..e444af7e7 --- /dev/null +++ b/src/main/java/pairmatching/dto/PairMatchingResultDto.java @@ -0,0 +1,17 @@ +package pairmatching.dto; + +import java.util.List; + +public class PairMatchingResultDto { + + private final List> pairMatchingResult; + + private PairMatchingResultDto(List> pairMatchingResult) { + this.pairMatchingResult = pairMatchingResult; + } + + public static PairMatchingResultDto of(List> pairMatchingResult) { + return new PairMatchingResultDto(pairMatchingResult); + } + +} diff --git a/src/main/java/pairmatching/model/Crew.java b/src/main/java/pairmatching/model/Crew.java index 637c80ecb..3cbdb7fbc 100644 --- a/src/main/java/pairmatching/model/Crew.java +++ b/src/main/java/pairmatching/model/Crew.java @@ -14,4 +14,8 @@ public static Crew from(Course course, String name) { return new Crew(course, name); } + public String getName() { + return name; + } + } diff --git a/src/main/java/pairmatching/model/Crews.java b/src/main/java/pairmatching/model/Crews.java index 4532da356..02ab6f048 100644 --- a/src/main/java/pairmatching/model/Crews.java +++ b/src/main/java/pairmatching/model/Crews.java @@ -1,7 +1,9 @@ package pairmatching.model; +import camp.nextstep.edu.missionutils.Randoms; import java.util.ArrayList; import java.util.List; +import pairmatching.dto.PairMatchingResultDto; public class Crews { @@ -19,4 +21,31 @@ public static Crews from(List names, Course course) { return new Crews(crews); } + public PairMatchingResultDto pairMatching() { + List crewNames = new ArrayList<>(); + for (Crew crew : crews) { + crewNames.add(crew.getName()); + } + + List shuffledCrew = Randoms.shuffle(crewNames); + return makePair(shuffledCrew); + } + + private PairMatchingResultDto makePair(List crewNames) { + List> pairs = new ArrayList<>(); + for (int i = 0; i < crewNames.size(); i += 2) { + List pair = new ArrayList<>(); + pair.add(crewNames.get(i)); + pair.add(crewNames.get(i + 1)); + pairs.add(pair); + } + + // 홀수면 마지막 pair는 3명이 한 팀 + if (crewNames.size() % 2 != 0) { + pairs.get(pairs.size() - 1).add(crewNames.get(crewNames.size() - 1)); + } + + return PairMatchingResultDto.of(pairs); + } + } diff --git a/src/main/java/pairmatching/service/InputParser.java b/src/main/java/pairmatching/service/InputParser.java new file mode 100644 index 000000000..1335ff5e9 --- /dev/null +++ b/src/main/java/pairmatching/service/InputParser.java @@ -0,0 +1,15 @@ +package pairmatching.service; + +import pairmatching.dto.PairMatchingDto; + +public class InputParser { + + private InputParser() { + } + + public static PairMatchingDto parsePairMatchingInformation(String input) { + String[] split = input.split(","); + return PairMatchingDto.of(split[0], split[1], split[2]); + } + +} From 0973b1f9d2f695e1f55be9c85b67a0a596c97c17 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 19:01:15 +0900 Subject: [PATCH 11/30] =?UTF-8?q?fix:=20=ED=8E=98=EC=96=B4=20=EB=A7=A4?= =?UTF-8?q?=EC=B9=AD=20=EC=9E=85=EB=A0=A5=20=EB=B0=A9=EC=8B=9D=20=EB=B3=80?= =?UTF-8?q?=EA=B2=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pairmatching/controller/Controller.java | 31 -------------- .../pairmatching/dto/PairMatchingDto.java | 41 ------------------- .../dto/PairMatchingResultDto.java | 17 -------- .../pairmatching/service/InputParser.java | 10 ++--- 4 files changed, 4 insertions(+), 95 deletions(-) delete mode 100644 src/main/java/pairmatching/dto/PairMatchingDto.java delete mode 100644 src/main/java/pairmatching/dto/PairMatchingResultDto.java diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index 041d4f473..8b4da83b9 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -3,15 +3,10 @@ import static pairmatching.service.FileReaderService.BACKEND_CREW_DIR; import static pairmatching.service.FileReaderService.FRONTEND_CREW_DIR; -import java.util.HashMap; import java.util.List; -import java.util.Map; -import pairmatching.dto.PairMatchingDto; -import pairmatching.dto.PairMatchingResultDto; import pairmatching.model.Course; import pairmatching.model.Crews; import pairmatching.service.FileReaderService; -import pairmatching.service.InputParser; import pairmatching.view.InputView; import pairmatching.view.OutputView; @@ -29,19 +24,6 @@ public void run() { Crews backendCrews = readCrews(BACKEND_CREW_DIR, Course.BACKEND); Crews frontendCrews = readCrews(FRONTEND_CREW_DIR, Course.FRONTEND); - Map pairMatchingResults = new HashMap<>(); - String function; - while (!"Q".equals(function = inputView.readFunctionSelect())) { - if ("1".equals(function)) { - matchPairs(pairMatchingResults, backendCrews, frontendCrews); - } - if ("2".equals(function)) { - return; - } - if ("3".equals(function)) { - return; - } - } } private Crews readCrews(String dir, Course course) { @@ -49,17 +31,4 @@ private Crews readCrews(String dir, Course course) { return Crews.from(names, course); } - private void matchPairs(Map pairMatchingResults, - Crews backendCrews, Crews frontendCrews) { - PairMatchingDto pairMatchingDto = InputParser.parsePairMatchingInformation( - inputView.readPairMatchingInformation()); - - if (pairMatchingDto.isBackend()) { - pairMatchingResults.put(pairMatchingDto, backendCrews.pairMatching()); - return; - } - pairMatchingResults.put(pairMatchingDto, frontendCrews.pairMatching()); - //validate - } - } diff --git a/src/main/java/pairmatching/dto/PairMatchingDto.java b/src/main/java/pairmatching/dto/PairMatchingDto.java deleted file mode 100644 index 8584df1e5..000000000 --- a/src/main/java/pairmatching/dto/PairMatchingDto.java +++ /dev/null @@ -1,41 +0,0 @@ -package pairmatching.dto; - -import java.util.Objects; -import pairmatching.model.Course; - -public class PairMatchingDto { - - private final String course; - private final String level; - private final String mission; - - private PairMatchingDto(String course, String level, String mission) { - this.course = course; - this.level = level; - this.mission = mission; - } - - public static PairMatchingDto of(String course, String level, String mission) { - return new PairMatchingDto(course, level, mission); - } - - public boolean isBackend() { - return Course.BACKEND.name().equals(course); - } - - @Override - public boolean equals(Object o) { - if (o == null || getClass() != o.getClass()) { - return false; - } - PairMatchingDto that = (PairMatchingDto) o; - return Objects.equals(course, that.course) && Objects.equals(level, that.level) - && Objects.equals(mission, that.mission); - } - - @Override - public int hashCode() { - return Objects.hash(course, level, mission); - } - -} diff --git a/src/main/java/pairmatching/dto/PairMatchingResultDto.java b/src/main/java/pairmatching/dto/PairMatchingResultDto.java deleted file mode 100644 index e444af7e7..000000000 --- a/src/main/java/pairmatching/dto/PairMatchingResultDto.java +++ /dev/null @@ -1,17 +0,0 @@ -package pairmatching.dto; - -import java.util.List; - -public class PairMatchingResultDto { - - private final List> pairMatchingResult; - - private PairMatchingResultDto(List> pairMatchingResult) { - this.pairMatchingResult = pairMatchingResult; - } - - public static PairMatchingResultDto of(List> pairMatchingResult) { - return new PairMatchingResultDto(pairMatchingResult); - } - -} diff --git a/src/main/java/pairmatching/service/InputParser.java b/src/main/java/pairmatching/service/InputParser.java index 1335ff5e9..b79e113e9 100644 --- a/src/main/java/pairmatching/service/InputParser.java +++ b/src/main/java/pairmatching/service/InputParser.java @@ -1,15 +1,13 @@ package pairmatching.service; -import pairmatching.dto.PairMatchingDto; - public class InputParser { private InputParser() { } - public static PairMatchingDto parsePairMatchingInformation(String input) { - String[] split = input.split(","); - return PairMatchingDto.of(split[0], split[1], split[2]); - } +// public static PairMatchingDto parsePairMatchingInformation(String input) { +// String[] split = input.split(","); +// return PairMatchingDto.of(split[0], split[1], split[2]); +// } } From 4128065b034ffb05ae327363d1f0666e3881954f Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 19:06:55 +0900 Subject: [PATCH 12/30] =?UTF-8?q?feat:=20=ED=8E=98=EC=96=B4=20=EC=B4=88?= =?UTF-8?q?=EA=B8=B0=ED=99=94=20=EA=B8=B0=EB=8A=A5=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pairmatching/controller/Controller.java | 14 ++++++++++++ src/main/java/pairmatching/model/Result.java | 22 +++++++++++++++++++ 2 files changed, 36 insertions(+) create mode 100644 src/main/java/pairmatching/model/Result.java diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index 8b4da83b9..96904d564 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -6,6 +6,7 @@ import java.util.List; import pairmatching.model.Course; import pairmatching.model.Crews; +import pairmatching.model.Result; import pairmatching.service.FileReaderService; import pairmatching.view.InputView; import pairmatching.view.OutputView; @@ -24,6 +25,19 @@ public void run() { Crews backendCrews = readCrews(BACKEND_CREW_DIR, Course.BACKEND); Crews frontendCrews = readCrews(FRONTEND_CREW_DIR, Course.FRONTEND); + Result result = Result.init(); + String function; + while (!"Q".equals(function = inputView.readFunctionSelect())) { + if ("1".equals(function)) { + return; + } + if ("2".equals(function)) { + return; + } + if ("3".equals(function)) { + result.reset(); + } + } } private Crews readCrews(String dir, Course course) { diff --git a/src/main/java/pairmatching/model/Result.java b/src/main/java/pairmatching/model/Result.java new file mode 100644 index 000000000..83d28efce --- /dev/null +++ b/src/main/java/pairmatching/model/Result.java @@ -0,0 +1,22 @@ +package pairmatching.model; + +import java.util.HashMap; +import java.util.Map; + +public class Result { + + private Map> result; + + private Result() { + this.result = new HashMap<>(); + } + + public static Result init() { + return new Result(); + } + + public void reset() { + result = new HashMap<>(); + } + +} From 84b8784cbd4f2413a1e24a53ef29b675c3a3360a Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 19:12:41 +0900 Subject: [PATCH 13/30] =?UTF-8?q?feat:=20=EA=B3=BC=EC=A0=95=20=EB=A0=88?= =?UTF-8?q?=EB=B2=A8=20=EB=AF=B8=EC=85=98=EC=9D=84=20=EC=84=A0=ED=83=9D?= =?UTF-8?q?=EB=B0=9B=EB=8A=94=20=EA=B8=B0=EB=8A=A5=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pairmatching/controller/Controller.java | 19 ++++++++++++++----- .../java/pairmatching/model/Information.java | 19 +++++++++++++++++++ .../pairmatching/service/InputParser.java | 10 ++++++---- .../java/pairmatching/view/InputView.java | 2 +- 4 files changed, 40 insertions(+), 10 deletions(-) create mode 100644 src/main/java/pairmatching/model/Information.java diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index 96904d564..1577b9543 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -6,8 +6,10 @@ import java.util.List; import pairmatching.model.Course; import pairmatching.model.Crews; +import pairmatching.model.Information; import pairmatching.model.Result; import pairmatching.service.FileReaderService; +import pairmatching.service.InputParser; import pairmatching.view.InputView; import pairmatching.view.OutputView; @@ -28,14 +30,17 @@ public void run() { Result result = Result.init(); String function; while (!"Q".equals(function = inputView.readFunctionSelect())) { + if ("3".equals(function)) { + result.reset(); + continue; + } + + Information courseAndLevelAndMission = readCourseAndLevelAndMission(); if ("1".equals(function)) { - return; + + continue; } if ("2".equals(function)) { - return; - } - if ("3".equals(function)) { - result.reset(); } } } @@ -45,4 +50,8 @@ private Crews readCrews(String dir, Course course) { return Crews.from(names, course); } + private Information readCourseAndLevelAndMission() { + return InputParser.parseCourseAndLevelAndMission(inputView.readCourseAndLevelAndMission()); + } + } diff --git a/src/main/java/pairmatching/model/Information.java b/src/main/java/pairmatching/model/Information.java new file mode 100644 index 000000000..166efa743 --- /dev/null +++ b/src/main/java/pairmatching/model/Information.java @@ -0,0 +1,19 @@ +package pairmatching.model; + +public class Information { + + private final Course course; + private final Level level; + private final Mission mission; + + private Information(Course course, Level level, Mission mission) { + this.course = course; + this.level = level; + this.mission = mission; + } + + public static Information from(String course, String level, String mission) { + return new Information(Course.valueOf(course), Level.valueOf(level), Mission.valueOf(mission)); + } + +} diff --git a/src/main/java/pairmatching/service/InputParser.java b/src/main/java/pairmatching/service/InputParser.java index b79e113e9..74d0fb80d 100644 --- a/src/main/java/pairmatching/service/InputParser.java +++ b/src/main/java/pairmatching/service/InputParser.java @@ -1,13 +1,15 @@ package pairmatching.service; +import pairmatching.model.Information; + public class InputParser { private InputParser() { } -// public static PairMatchingDto parsePairMatchingInformation(String input) { -// String[] split = input.split(","); -// return PairMatchingDto.of(split[0], split[1], split[2]); -// } + public static Information parseCourseAndLevelAndMission(String input) { + String[] split = input.split(","); + return Information.from(split[0], split[1], split[2]); + } } diff --git a/src/main/java/pairmatching/view/InputView.java b/src/main/java/pairmatching/view/InputView.java index cea0adce7..a8bf03b6f 100644 --- a/src/main/java/pairmatching/view/InputView.java +++ b/src/main/java/pairmatching/view/InputView.java @@ -15,7 +15,7 @@ public String readFunctionSelect() { return Console.readLine(); } - public String readPairMatchingInformation() { + public String readCourseAndLevelAndMission() { System.out.println(); printWooWaInformation(); System.out.println("과정, 레벨, 미션을 선택하세요."); From 2107ee094d34ed387ee3079fc5f26676fe6906f6 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 19:25:06 +0900 Subject: [PATCH 14/30] =?UTF-8?q?refactor:=20=EC=82=AC=EC=9A=A9=ED=95=98?= =?UTF-8?q?=EC=A7=80=EC=95=8A=EB=8A=94=20=EB=A9=94=EC=84=9C=EB=93=9C=20?= =?UTF-8?q?=EC=82=AD=EC=A0=9C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/pairmatching/model/Crews.java | 28 --------------------- 1 file changed, 28 deletions(-) diff --git a/src/main/java/pairmatching/model/Crews.java b/src/main/java/pairmatching/model/Crews.java index 02ab6f048..0fa3fa434 100644 --- a/src/main/java/pairmatching/model/Crews.java +++ b/src/main/java/pairmatching/model/Crews.java @@ -1,9 +1,7 @@ package pairmatching.model; -import camp.nextstep.edu.missionutils.Randoms; import java.util.ArrayList; import java.util.List; -import pairmatching.dto.PairMatchingResultDto; public class Crews { @@ -21,31 +19,5 @@ public static Crews from(List names, Course course) { return new Crews(crews); } - public PairMatchingResultDto pairMatching() { - List crewNames = new ArrayList<>(); - for (Crew crew : crews) { - crewNames.add(crew.getName()); - } - - List shuffledCrew = Randoms.shuffle(crewNames); - return makePair(shuffledCrew); - } - - private PairMatchingResultDto makePair(List crewNames) { - List> pairs = new ArrayList<>(); - for (int i = 0; i < crewNames.size(); i += 2) { - List pair = new ArrayList<>(); - pair.add(crewNames.get(i)); - pair.add(crewNames.get(i + 1)); - pairs.add(pair); - } - - // 홀수면 마지막 pair는 3명이 한 팀 - if (crewNames.size() % 2 != 0) { - pairs.get(pairs.size() - 1).add(crewNames.get(crewNames.size() - 1)); - } - - return PairMatchingResultDto.of(pairs); - } } From 5b4e712d68971c2bbf3ac084b33658d9e2817b40 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 19:32:58 +0900 Subject: [PATCH 15/30] =?UTF-8?q?refactor:=20course=EB=B3=84=EB=A1=9C=20?= =?UTF-8?q?=EC=9D=B8=EC=9B=90=EC=9D=84=20=EB=8B=B4=EB=8F=84=EB=A1=9D=20Cre?= =?UTF-8?q?ws=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pairmatching/controller/Controller.java | 33 ++++++++++++++----- src/main/java/pairmatching/model/Crews.java | 18 +++------- .../java/pairmatching/model/Information.java | 19 ----------- .../pairmatching/model/InputInformation.java | 31 +++++++++++++++++ .../pairmatching/service/InputParser.java | 6 ++-- 5 files changed, 64 insertions(+), 43 deletions(-) delete mode 100644 src/main/java/pairmatching/model/Information.java create mode 100644 src/main/java/pairmatching/model/InputInformation.java diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index 1577b9543..82f6765fe 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -3,10 +3,12 @@ import static pairmatching.service.FileReaderService.BACKEND_CREW_DIR; import static pairmatching.service.FileReaderService.FRONTEND_CREW_DIR; +import java.util.ArrayList; import java.util.List; import pairmatching.model.Course; +import pairmatching.model.Crew; import pairmatching.model.Crews; -import pairmatching.model.Information; +import pairmatching.model.InputInformation; import pairmatching.model.Result; import pairmatching.service.FileReaderService; import pairmatching.service.InputParser; @@ -24,8 +26,9 @@ public Controller(InputView inputView, OutputView outputView) { } public void run() { - Crews backendCrews = readCrews(BACKEND_CREW_DIR, Course.BACKEND); - Crews frontendCrews = readCrews(FRONTEND_CREW_DIR, Course.FRONTEND); + List backendCrews = readCrews(BACKEND_CREW_DIR, Course.BACKEND); + List frontendCrews = readCrews(FRONTEND_CREW_DIR, Course.FRONTEND); + Crews crews = new Crews(backendCrews, frontendCrews); Result result = Result.init(); String function; @@ -35,9 +38,9 @@ public void run() { continue; } - Information courseAndLevelAndMission = readCourseAndLevelAndMission(); + InputInformation courseAndLevelAndMission = readCourseAndLevelAndMission(); if ("1".equals(function)) { - + handlePairMatching(result, courseAndLevelAndMission); continue; } if ("2".equals(function)) { @@ -45,13 +48,27 @@ public void run() { } } - private Crews readCrews(String dir, Course course) { + private List readCrews(String dir, Course course) { List names = FileReaderService.readFile(dir); - return Crews.from(names, course); + List crews = new ArrayList<>(); + for (String name : names) { + crews.add(Crew.from(course, name)); + } + return crews; } - private Information readCourseAndLevelAndMission() { + private InputInformation readCourseAndLevelAndMission() { return InputParser.parseCourseAndLevelAndMission(inputView.readCourseAndLevelAndMission()); } + private void handlePairMatching(Result result, InputInformation information) { + Course course = information.getCourse(); + if (course == Course.BACKEND) { + + } + if (course == Course.FRONTEND) { + + } + } + } diff --git a/src/main/java/pairmatching/model/Crews.java b/src/main/java/pairmatching/model/Crews.java index 0fa3fa434..61d1c19ca 100644 --- a/src/main/java/pairmatching/model/Crews.java +++ b/src/main/java/pairmatching/model/Crews.java @@ -1,23 +1,15 @@ package pairmatching.model; -import java.util.ArrayList; import java.util.List; public class Crews { - private final List crews; + private final List backends; + private final List frontends; - private Crews(List crews) { - this.crews = crews; + public Crews(List backends, List frontends) { + this.backends = backends; + this.frontends = frontends; } - public static Crews from(List names, Course course) { - List crews = new ArrayList<>(); - for (String name : names) { - crews.add(Crew.from(course, name)); - } - return new Crews(crews); - } - - } diff --git a/src/main/java/pairmatching/model/Information.java b/src/main/java/pairmatching/model/Information.java deleted file mode 100644 index 166efa743..000000000 --- a/src/main/java/pairmatching/model/Information.java +++ /dev/null @@ -1,19 +0,0 @@ -package pairmatching.model; - -public class Information { - - private final Course course; - private final Level level; - private final Mission mission; - - private Information(Course course, Level level, Mission mission) { - this.course = course; - this.level = level; - this.mission = mission; - } - - public static Information from(String course, String level, String mission) { - return new Information(Course.valueOf(course), Level.valueOf(level), Mission.valueOf(mission)); - } - -} diff --git a/src/main/java/pairmatching/model/InputInformation.java b/src/main/java/pairmatching/model/InputInformation.java new file mode 100644 index 000000000..686e28e9d --- /dev/null +++ b/src/main/java/pairmatching/model/InputInformation.java @@ -0,0 +1,31 @@ +package pairmatching.model; + +public class InputInformation { + + private final Course course; + private final Level level; + private final Mission mission; + + private InputInformation(Course course, Level level, Mission mission) { + this.course = course; + this.level = level; + this.mission = mission; + } + + public static InputInformation from(String course, String level, String mission) { + return new InputInformation(Course.valueOf(course), Level.valueOf(level), Mission.valueOf(mission)); + } + + public Course getCourse() { + return course; + } + + public Level getLevel() { + return level; + } + + public Mission getMission() { + return mission; + } + +} diff --git a/src/main/java/pairmatching/service/InputParser.java b/src/main/java/pairmatching/service/InputParser.java index 74d0fb80d..9428559fd 100644 --- a/src/main/java/pairmatching/service/InputParser.java +++ b/src/main/java/pairmatching/service/InputParser.java @@ -1,15 +1,15 @@ package pairmatching.service; -import pairmatching.model.Information; +import pairmatching.model.InputInformation; public class InputParser { private InputParser() { } - public static Information parseCourseAndLevelAndMission(String input) { + public static InputInformation parseCourseAndLevelAndMission(String input) { String[] split = input.split(","); - return Information.from(split[0], split[1], split[2]); + return InputInformation.from(split[0], split[1], split[2]); } } From 09972c767bc5057146b4df27f8bf5c556f0a501f Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 19:44:21 +0900 Subject: [PATCH 16/30] =?UTF-8?q?feat:=20=ED=8E=98=EC=96=B4=EB=A5=BC=20?= =?UTF-8?q?=EA=B5=AC=ED=95=98=EB=8A=94=20=EA=B8=B0=EB=8A=A5=20=EA=B5=AC?= =?UTF-8?q?=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pairmatching/controller/Controller.java | 14 +++---- src/main/java/pairmatching/model/Crews.java | 37 +++++++++++++++++-- 2 files changed, 38 insertions(+), 13 deletions(-) diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index 82f6765fe..bf5a29325 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -40,7 +40,7 @@ public void run() { InputInformation courseAndLevelAndMission = readCourseAndLevelAndMission(); if ("1".equals(function)) { - handlePairMatching(result, courseAndLevelAndMission); + handlePairMatching(result, courseAndLevelAndMission, crews); continue; } if ("2".equals(function)) { @@ -61,14 +61,10 @@ private InputInformation readCourseAndLevelAndMission() { return InputParser.parseCourseAndLevelAndMission(inputView.readCourseAndLevelAndMission()); } - private void handlePairMatching(Result result, InputInformation information) { - Course course = information.getCourse(); - if (course == Course.BACKEND) { - - } - if (course == Course.FRONTEND) { - - } + private void handlePairMatching(Result result, InputInformation information, Crews crews) { + // TODO: result를 보고 이미 있는 정보인지 확인. + List> pairs = crews.pairMatching(information.getCourse()); + // TODO: result와 비교하여 같은 레벨 중복이 없는지. } } diff --git a/src/main/java/pairmatching/model/Crews.java b/src/main/java/pairmatching/model/Crews.java index 61d1c19ca..cd3802694 100644 --- a/src/main/java/pairmatching/model/Crews.java +++ b/src/main/java/pairmatching/model/Crews.java @@ -1,15 +1,44 @@ package pairmatching.model; +import camp.nextstep.edu.missionutils.Randoms; +import java.util.ArrayList; +import java.util.HashMap; import java.util.List; +import java.util.Map; public class Crews { - private final List backends; - private final List frontends; + private final Map> crews; public Crews(List backends, List frontends) { - this.backends = backends; - this.frontends = frontends; + this.crews = new HashMap<>(); + crews.put(Course.BACKEND, backends); + crews.put(Course.FRONTEND, frontends); + } + + public List> pairMatching(Course course) { + List crewNames = new ArrayList<>(); + for (Crew crew : crews.get(course)) { + crewNames.add(crew.getName()); + } + + return makePair(Randoms.shuffle(crewNames)); + } + + private List> makePair(List crewNames) { + List> pairs = new ArrayList<>(); + for (int i = 0; i < crewNames.size(); i += 2) { + List pair = new ArrayList<>(); + pair.add(crewNames.get(i)); + pair.add(crewNames.get(i + 1)); + pairs.add(pair); + } + + if (crewNames.size() % 2 != 0) { + pairs.get(pairs.size() - 1).add(crewNames.get(crewNames.size() - 1)); + } + + return pairs; } } From 1b13a9513f22d08364fd72054316919ca17de1f5 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 19:49:38 +0900 Subject: [PATCH 17/30] =?UTF-8?q?feat:=20=EC=9D=B4=EB=AF=B8=20=EB=A7=A4?= =?UTF-8?q?=EC=B9=AD=EB=90=9C=20=EA=B2=B0=EA=B3=BC=EA=B0=80=20=EC=9E=88?= =?UTF-8?q?=EB=8A=94=EC=A7=80=20=ED=99=95=EC=9D=B8=ED=95=98=EB=8A=94=20?= =?UTF-8?q?=EA=B8=B0=EB=8A=A5=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/pairmatching/controller/Controller.java | 7 ++++++- src/main/java/pairmatching/model/Result.java | 9 ++++++++- src/main/java/pairmatching/view/InputView.java | 7 +++++++ 3 files changed, 21 insertions(+), 2 deletions(-) diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index bf5a29325..bd0f3bf17 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -62,7 +62,12 @@ private InputInformation readCourseAndLevelAndMission() { } private void handlePairMatching(Result result, InputInformation information, Crews crews) { - // TODO: result를 보고 이미 있는 정보인지 확인. + if (result.isExist(information)) { + String rematching = inputView.readRematching(); + if ("아니오".equals(rematching)) { + return; + } + } List> pairs = crews.pairMatching(information.getCourse()); // TODO: result와 비교하여 같은 레벨 중복이 없는지. } diff --git a/src/main/java/pairmatching/model/Result.java b/src/main/java/pairmatching/model/Result.java index 83d28efce..e158f959b 100644 --- a/src/main/java/pairmatching/model/Result.java +++ b/src/main/java/pairmatching/model/Result.java @@ -1,11 +1,12 @@ package pairmatching.model; import java.util.HashMap; +import java.util.List; import java.util.Map; public class Result { - private Map> result; + private Map>>>> result; private Result() { this.result = new HashMap<>(); @@ -19,4 +20,10 @@ public void reset() { result = new HashMap<>(); } + public boolean isExist(InputInformation information) { + return result.get(information.getCourse()) + .get(information.getLevel()) + .get(information.getMission()) != null; + } + } diff --git a/src/main/java/pairmatching/view/InputView.java b/src/main/java/pairmatching/view/InputView.java index a8bf03b6f..0f7787ee9 100644 --- a/src/main/java/pairmatching/view/InputView.java +++ b/src/main/java/pairmatching/view/InputView.java @@ -23,6 +23,13 @@ public String readCourseAndLevelAndMission() { return Console.readLine(); } + public String readRematching() { + System.out.println(); + System.out.println("매칭 정보가 있습니다. 다시 매칭하시겠습니까?"); + System.out.println("네 | 아니오"); + return Console.readLine(); + } + private void printWooWaInformation() { System.out.println("#############################################"); System.out.println("과정: " + Course.BACKEND.name() + " | " + Course.FRONTEND.name()); From 08bf621a0ca51e9cb1418131b1968b5bb36c25c1 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 22:26:31 +0900 Subject: [PATCH 18/30] =?UTF-8?q?feat:=20=EA=B2=B0=EA=B3=BC=EB=A5=BC=20?= =?UTF-8?q?=EC=A0=80=EC=9E=A5=ED=95=98=EB=8A=94=20=EB=A1=9C=EC=A7=81=20?= =?UTF-8?q?=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pairmatching/controller/Controller.java | 3 ++- src/main/java/pairmatching/model/Result.java | 21 +++++++++++++++---- 2 files changed, 19 insertions(+), 5 deletions(-) diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index bd0f3bf17..c0fd8b93a 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -34,7 +34,7 @@ public void run() { String function; while (!"Q".equals(function = inputView.readFunctionSelect())) { if ("3".equals(function)) { - result.reset(); + result = Result.init(); continue; } @@ -69,6 +69,7 @@ private void handlePairMatching(Result result, InputInformation information, Cre } } List> pairs = crews.pairMatching(information.getCourse()); + result.put(information, pairs); // TODO: result와 비교하여 같은 레벨 중복이 없는지. } diff --git a/src/main/java/pairmatching/model/Result.java b/src/main/java/pairmatching/model/Result.java index e158f959b..82f2854fc 100644 --- a/src/main/java/pairmatching/model/Result.java +++ b/src/main/java/pairmatching/model/Result.java @@ -9,21 +9,34 @@ public class Result { private Map>>>> result; private Result() { + Map>> missionTemp = new HashMap<>(); + for (Mission mission : Mission.values()) { + missionTemp.put(mission, null); + } + Map>>> levelTemp = new HashMap<>(); + for (Level level : Level.values()) { + levelTemp.put(level, missionTemp); + } this.result = new HashMap<>(); + for (Course course : Course.values()) { + result.put(course, levelTemp); + } } public static Result init() { return new Result(); } - public void reset() { - result = new HashMap<>(); - } - public boolean isExist(InputInformation information) { return result.get(information.getCourse()) .get(information.getLevel()) .get(information.getMission()) != null; } + public void put(InputInformation information, List> pairs) { + result.get(information.getCourse()) + .get(information.getLevel()) + .put(information.getMission(), pairs); + } + } From ca4ffe824f4d51bc8b294b0ff71f01d0d106a9b1 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 22:40:16 +0900 Subject: [PATCH 19/30] =?UTF-8?q?feat:=20=EB=AF=B8=EC=85=98=EC=9D=B4=20?= =?UTF-8?q?=EB=A0=88=EB=B2=A8=EC=9D=84=20=ED=8F=AC=ED=95=A8=ED=95=98?= =?UTF-8?q?=EB=8F=84=EB=A1=9D=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/pairmatching/model/Mission.java | 20 ++++++++++--------- 1 file changed, 11 insertions(+), 9 deletions(-) diff --git a/src/main/java/pairmatching/model/Mission.java b/src/main/java/pairmatching/model/Mission.java index 32b77136c..f0a549580 100644 --- a/src/main/java/pairmatching/model/Mission.java +++ b/src/main/java/pairmatching/model/Mission.java @@ -2,21 +2,23 @@ public enum Mission { - RACING_CAR("자동차경주"), - LOTTO("로또"), - NUMBER_BASEBALL("숫자야구게임"), + RACING_CAR("자동차경주", Level.LEVEL1), + LOTTO("로또", Level.LEVEL1), + NUMBER_BASEBALL("숫자야구게임", Level.LEVEL1), - SHOPPING_CART("장바구니"), - PAYMENT("결제"), - SUBWAY("지하철노선도"), + SHOPPING_CART("장바구니", Level.LEVEL2), + PAYMENT("결제", Level.LEVEL2), + SUBWAY("지하철노선도", Level.LEVEL2), - IMPROVEMENT("성능개선"), - DEPLOY("배포"); + IMPROVEMENT("성능개선", Level.LEVEL4), + DEPLOY("배포", Level.LEVEL4); private final String name; + private final Level level; - Mission(String name) { + Mission(String name, Level level) { this.name = name; + this.level = level; } public static String level1() { From 153361731092314062c3c5a4cfe3ed44b3618615 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 22:46:43 +0900 Subject: [PATCH 20/30] =?UTF-8?q?fix:=20=EB=A0=88=EB=B2=A8=EB=B3=84?= =?UTF-8?q?=EB=A1=9C=20=EB=8B=A4=EB=A5=B8=20=EB=AF=B8=EC=85=98=EC=9D=B4=20?= =?UTF-8?q?=ED=8F=AC=ED=95=A8=EB=90=98=EB=8F=84=EB=A1=9D=20=EB=B3=80?= =?UTF-8?q?=EA=B2=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/pairmatching/model/Result.java | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/src/main/java/pairmatching/model/Result.java b/src/main/java/pairmatching/model/Result.java index 82f2854fc..81fcdee1f 100644 --- a/src/main/java/pairmatching/model/Result.java +++ b/src/main/java/pairmatching/model/Result.java @@ -9,17 +9,16 @@ public class Result { private Map>>>> result; private Result() { - Map>> missionTemp = new HashMap<>(); - for (Mission mission : Mission.values()) { - missionTemp.put(mission, null); - } - Map>>> levelTemp = new HashMap<>(); + Map>>> temp = new HashMap<>(); for (Level level : Level.values()) { - levelTemp.put(level, missionTemp); + temp.put(level, new HashMap<>()); + for (Mission mission : Mission.values(level)) { + temp.get(level).put(mission, null); + } } this.result = new HashMap<>(); for (Course course : Course.values()) { - result.put(course, levelTemp); + result.put(course, temp); } } From c5b085681ff1ac28fbd5d547ce6e7e1d12117ec2 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 23:08:09 +0900 Subject: [PATCH 21/30] =?UTF-8?q?feat:=20=ED=8E=98=EC=96=B4=20=EB=A7=A4?= =?UTF-8?q?=EC=B9=AD=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pairmatching/controller/Controller.java | 19 +++++-- src/main/java/pairmatching/model/Mission.java | 13 +++++ src/main/java/pairmatching/model/Result.java | 50 +++++++++++++++++++ 3 files changed, 79 insertions(+), 3 deletions(-) diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index c0fd8b93a..c19863c92 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -62,15 +62,28 @@ private InputInformation readCourseAndLevelAndMission() { } private void handlePairMatching(Result result, InputInformation information, Crews crews) { + // 이미 생성된 정보가 있을 때 if (result.isExist(information)) { String rematching = inputView.readRematching(); if ("아니오".equals(rematching)) { return; } } - List> pairs = crews.pairMatching(information.getCourse()); - result.put(information, pairs); - // TODO: result와 비교하여 같은 레벨 중복이 없는지. + + int retry = 0; + while (retry < 3) { + try { + // 정보 생성 및 저장 + List> pairs = crews.pairMatching(information.getCourse()); + result.put(information, pairs); + // 같은 레벨에서 같은 크루가 두 번 이상 만나는지 검사 + result.isAlreadyMatched(); + return; + } catch (IllegalArgumentException e) { + retry++; + } + } + throw new IllegalArgumentException("3회 시도까지 매칭이 되지 않았습니다."); } } diff --git a/src/main/java/pairmatching/model/Mission.java b/src/main/java/pairmatching/model/Mission.java index f0a549580..7dd5bde01 100644 --- a/src/main/java/pairmatching/model/Mission.java +++ b/src/main/java/pairmatching/model/Mission.java @@ -1,5 +1,8 @@ package pairmatching.model; +import java.util.ArrayList; +import java.util.List; + public enum Mission { RACING_CAR("자동차경주", Level.LEVEL1), @@ -21,6 +24,16 @@ public enum Mission { this.level = level; } + public static List values(Level level) { + List missions = new ArrayList<>(); + for (Mission mission : Mission.values()) { + if (mission.level == level) { + missions.add(mission); + } + } + return missions; + } + public static String level1() { return RACING_CAR.name + " | " + LOTTO.name + " | " + NUMBER_BASEBALL; } diff --git a/src/main/java/pairmatching/model/Result.java b/src/main/java/pairmatching/model/Result.java index 81fcdee1f..27a1d1614 100644 --- a/src/main/java/pairmatching/model/Result.java +++ b/src/main/java/pairmatching/model/Result.java @@ -38,4 +38,54 @@ public void put(InputInformation information, List> pairs) { .put(information.getMission(), pairs); } + public void isAlreadyMatched() { + for (Course course : Course.values()) { + for (Level level : Level.values()) { + validateAlreadyMatched(result.get(course).get(level), level); + } + } + } + + private void validateAlreadyMatched(Map>> sameLevelPairs, Level level) { + if (sameLevelPairs.isEmpty()) { + return; + } + + for (Mission x : Mission.values(level)) { + for (Mission y : Mission.values(level)) { + checkSameLevel(sameLevelPairs, x, y); + } + } + } + + private void checkSameLevel(Map>> sameLevelPairs, Mission x, Mission y) { + if (x == y) { + return; + } + + List> pairsX = sameLevelPairs.get(x); + List> pairsY = sameLevelPairs.get(y); + for (int i = 0; i < pairsX.size(); i++) { + for (int j = i + 1; j < pairsY.size(); j++) { + check(pairsX.get(i), pairsY.get(j)); + } + } + } + + private void check(List pairX, List pairY) { + if (pairX.size() != pairY.size()) { + return; + } + + pairX.sort(String::compareTo); + pairY.sort(String::compareTo); + + for (int i = 0; i < pairX.size(); i++) { + if (!pairX.get(i).equals(pairY.get(i))) { + return; + } + } + throw new IllegalArgumentException("중복되는 페어가 있으므로 다시 섞습니다."); + } + } From 2522c0ea64079f73a1286111782cfea3d40f5c91 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 23:18:05 +0900 Subject: [PATCH 22/30] =?UTF-8?q?feat:=20=EC=A1=B0=ED=9A=8C=EA=B8=B0?= =?UTF-8?q?=EB=8A=A5=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pairmatching/controller/Controller.java | 6 ++++++ src/main/java/pairmatching/model/Result.java | 8 ++++++-- src/main/java/pairmatching/view/OutputView.java | 17 +++++++++++++++++ 3 files changed, 29 insertions(+), 2 deletions(-) diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index c19863c92..6bfd994df 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -44,6 +44,7 @@ public void run() { continue; } if ("2".equals(function)) { + handlePrintPairMatching(result, courseAndLevelAndMission); } } } @@ -86,4 +87,9 @@ private void handlePairMatching(Result result, InputInformation information, Cre throw new IllegalArgumentException("3회 시도까지 매칭이 되지 않았습니다."); } + private void handlePrintPairMatching(Result result, InputInformation courseAndLevelAndMission) { + List> pairs = result.getPairs(courseAndLevelAndMission); + outputView.printPairMatching(pairs); + } + } diff --git a/src/main/java/pairmatching/model/Result.java b/src/main/java/pairmatching/model/Result.java index 27a1d1614..342978843 100644 --- a/src/main/java/pairmatching/model/Result.java +++ b/src/main/java/pairmatching/model/Result.java @@ -26,10 +26,14 @@ public static Result init() { return new Result(); } - public boolean isExist(InputInformation information) { + public List> getPairs(InputInformation information) { return result.get(information.getCourse()) .get(information.getLevel()) - .get(information.getMission()) != null; + .get(information.getMission()); + } + + public boolean isExist(InputInformation information) { + return getPairs(information) != null; } public void put(InputInformation information, List> pairs) { diff --git a/src/main/java/pairmatching/view/OutputView.java b/src/main/java/pairmatching/view/OutputView.java index 5a43c742c..f83fbecd6 100644 --- a/src/main/java/pairmatching/view/OutputView.java +++ b/src/main/java/pairmatching/view/OutputView.java @@ -1,4 +1,21 @@ package pairmatching.view; +import java.util.List; +import java.util.StringJoiner; + public class OutputView { + + public void printPairMatching(List> pairs) { + System.out.println(); + System.out.println("페어 매칭 결과입니다."); + + for (List pair : pairs) { + StringJoiner stringJoiner = new StringJoiner(" : "); + for (String name : pair) { + stringJoiner.add(name); + } + System.out.println(stringJoiner); + } + } + } From 05116eb28b721d0867332237f4a99b880e02a5fe Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 23:28:41 +0900 Subject: [PATCH 23/30] =?UTF-8?q?fix:=20=EC=A1=B0=ED=9A=8C=20=EA=B8=B0?= =?UTF-8?q?=EB=8A=A5=20=EC=98=A4=EB=A5=98=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/pairmatching/model/Course.java | 13 +++++++++++++ .../java/pairmatching/model/InputInformation.java | 6 +++++- src/main/java/pairmatching/model/Level.java | 9 +++++++++ src/main/java/pairmatching/model/Mission.java | 13 +++++++++++-- src/main/java/pairmatching/view/InputView.java | 12 ++++++------ src/main/java/pairmatching/view/OutputView.java | 6 +++++- 6 files changed, 49 insertions(+), 10 deletions(-) diff --git a/src/main/java/pairmatching/model/Course.java b/src/main/java/pairmatching/model/Course.java index 96bd878b0..f7f538f31 100644 --- a/src/main/java/pairmatching/model/Course.java +++ b/src/main/java/pairmatching/model/Course.java @@ -11,4 +11,17 @@ public enum Course { this.name = name; } + public static Course from(String name) { + for (Course course : Course.values()) { + if (course.name.equals(name)) { + return course; + } + } + throw new IllegalArgumentException("없는 과정입니다."); + } + + public String getName() { + return name; + } + } diff --git a/src/main/java/pairmatching/model/InputInformation.java b/src/main/java/pairmatching/model/InputInformation.java index 686e28e9d..1cfb8677c 100644 --- a/src/main/java/pairmatching/model/InputInformation.java +++ b/src/main/java/pairmatching/model/InputInformation.java @@ -13,7 +13,11 @@ private InputInformation(Course course, Level level, Mission mission) { } public static InputInformation from(String course, String level, String mission) { - return new InputInformation(Course.valueOf(course), Level.valueOf(level), Mission.valueOf(mission)); + return new InputInformation( + Course.from(course.trim()), + Level.from(level.trim()), + Mission.from(mission.trim()) + ); } public Course getCourse() { diff --git a/src/main/java/pairmatching/model/Level.java b/src/main/java/pairmatching/model/Level.java index 77a0182c0..147817eec 100644 --- a/src/main/java/pairmatching/model/Level.java +++ b/src/main/java/pairmatching/model/Level.java @@ -14,4 +14,13 @@ public enum Level { this.name = name; } + public static Level from(String name) { + for (Level level : Level.values()) { + if (level.name.equals(name)) { + return level; + } + } + throw new IllegalArgumentException("없는 레벨입니다."); + } + } diff --git a/src/main/java/pairmatching/model/Mission.java b/src/main/java/pairmatching/model/Mission.java index 7dd5bde01..9b4c7e5b3 100644 --- a/src/main/java/pairmatching/model/Mission.java +++ b/src/main/java/pairmatching/model/Mission.java @@ -34,12 +34,21 @@ public static List values(Level level) { return missions; } + public static Mission from(String name) { + for (Mission mission : Mission.values()) { + if (mission.name.equals(name)) { + return mission; + } + } + throw new IllegalArgumentException("없는 미션입니다."); + } + public static String level1() { - return RACING_CAR.name + " | " + LOTTO.name + " | " + NUMBER_BASEBALL; + return RACING_CAR.name + " | " + LOTTO.name + " | " + NUMBER_BASEBALL.name; } public static String level2() { - return SHOPPING_CART.name + " | " + PAYMENT.name + " | " + SUBWAY; + return SHOPPING_CART.name + " | " + PAYMENT.name + " | " + SUBWAY.name; } public static String level3() { diff --git a/src/main/java/pairmatching/view/InputView.java b/src/main/java/pairmatching/view/InputView.java index 0f7787ee9..e2a49d676 100644 --- a/src/main/java/pairmatching/view/InputView.java +++ b/src/main/java/pairmatching/view/InputView.java @@ -32,13 +32,13 @@ public String readRematching() { private void printWooWaInformation() { System.out.println("#############################################"); - System.out.println("과정: " + Course.BACKEND.name() + " | " + Course.FRONTEND.name()); + System.out.println("과정: " + Course.BACKEND.getName() + " | " + Course.FRONTEND.getName()); System.out.println("미션: "); - System.out.println(Mission.level1()); - System.out.println(Mission.level2()); - System.out.println(Mission.level3()); - System.out.println(Mission.level4()); - System.out.println(Mission.level5()); + System.out.println(" - 레벨1: " + Mission.level1()); + System.out.println(" - 레벨2: " + Mission.level2()); + System.out.println(" - 레벨3: " + Mission.level3()); + System.out.println(" - 레벨4: " + Mission.level4()); + System.out.println(" - 레벨5: " + Mission.level5()); System.out.println("#############################################"); } diff --git a/src/main/java/pairmatching/view/OutputView.java b/src/main/java/pairmatching/view/OutputView.java index f83fbecd6..a83c98001 100644 --- a/src/main/java/pairmatching/view/OutputView.java +++ b/src/main/java/pairmatching/view/OutputView.java @@ -7,8 +7,12 @@ public class OutputView { public void printPairMatching(List> pairs) { System.out.println(); - System.out.println("페어 매칭 결과입니다."); + if (pairs == null) { + System.out.println("페어 매칭 결과가 없습니다."); + return; + } + System.out.println("페어 매칭 결과입니다."); for (List pair : pairs) { StringJoiner stringJoiner = new StringJoiner(" : "); for (String name : pair) { From 24228095c60240c0244bf41708498e742e352c17 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 23:29:53 +0900 Subject: [PATCH 24/30] =?UTF-8?q?fix:=20=EB=A7=A4=EC=B9=AD=20=EA=B8=B0?= =?UTF-8?q?=EB=8A=A5=EB=8F=84=20=EC=A1=B0=ED=9A=8C=EA=B0=80=20=EB=90=98?= =?UTF-8?q?=EB=8F=84=EB=A1=9D=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/pairmatching/controller/Controller.java | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index 6bfd994df..ebc40b084 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -41,11 +41,8 @@ public void run() { InputInformation courseAndLevelAndMission = readCourseAndLevelAndMission(); if ("1".equals(function)) { handlePairMatching(result, courseAndLevelAndMission, crews); - continue; - } - if ("2".equals(function)) { - handlePrintPairMatching(result, courseAndLevelAndMission); } + handlePrintPairMatching(result, courseAndLevelAndMission); } } From e6bbfe48ae665ea1c444dff124d59a035c984567 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 23:33:27 +0900 Subject: [PATCH 25/30] =?UTF-8?q?fix:=20=ED=8E=98=EC=96=B4=20=EB=A7=A4?= =?UTF-8?q?=EC=B9=AD=20null=20point=20=EC=98=A4=EB=A5=98=20=EC=88=98?= =?UTF-8?q?=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/pairmatching/model/Result.java | 4 ++++ src/main/java/pairmatching/view/OutputView.java | 1 + 2 files changed, 5 insertions(+) diff --git a/src/main/java/pairmatching/model/Result.java b/src/main/java/pairmatching/model/Result.java index 342978843..46d21538a 100644 --- a/src/main/java/pairmatching/model/Result.java +++ b/src/main/java/pairmatching/model/Result.java @@ -69,6 +69,10 @@ private void checkSameLevel(Map>> sameLevelPairs, Mis List> pairsX = sameLevelPairs.get(x); List> pairsY = sameLevelPairs.get(y); + if (pairsX == null || pairsY == null) { + return; + } + for (int i = 0; i < pairsX.size(); i++) { for (int j = i + 1; j < pairsY.size(); j++) { check(pairsX.get(i), pairsY.get(j)); diff --git a/src/main/java/pairmatching/view/OutputView.java b/src/main/java/pairmatching/view/OutputView.java index a83c98001..661c02c08 100644 --- a/src/main/java/pairmatching/view/OutputView.java +++ b/src/main/java/pairmatching/view/OutputView.java @@ -20,6 +20,7 @@ public void printPairMatching(List> pairs) { } System.out.println(stringJoiner); } + System.out.println(); } } From a95e0e4b279257721a29ec36fd28ec01c7f71a9c Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 23:44:03 +0900 Subject: [PATCH 26/30] =?UTF-8?q?feat:=20=EC=9E=AC=EC=9E=85=EB=A0=A5=20?= =?UTF-8?q?=EB=A1=9C=EC=A7=81=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pairmatching/controller/Controller.java | 38 ++++++++++++++----- .../pairmatching/service/InputParser.java | 8 +++- .../java/pairmatching/view/OutputView.java | 4 ++ 3 files changed, 38 insertions(+), 12 deletions(-) diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index ebc40b084..ffaffde95 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -5,6 +5,7 @@ import java.util.ArrayList; import java.util.List; +import java.util.function.Supplier; import pairmatching.model.Course; import pairmatching.model.Crew; import pairmatching.model.Crews; @@ -37,26 +38,33 @@ public void run() { result = Result.init(); continue; } - - InputInformation courseAndLevelAndMission = readCourseAndLevelAndMission(); + if ("1".equals(function)) { + InputInformation courseAndLevelAndMission = readCourseAndLevelAndMission(); handlePairMatching(result, courseAndLevelAndMission, crews); } - handlePrintPairMatching(result, courseAndLevelAndMission); + if ("2".equals(function)) { + InputInformation courseAndLevelAndMission = readCourseAndLevelAndMission(); + handlePrintPairMatching(result, courseAndLevelAndMission); + } } } private List readCrews(String dir, Course course) { - List names = FileReaderService.readFile(dir); - List crews = new ArrayList<>(); - for (String name : names) { - crews.add(Crew.from(course, name)); - } - return crews; + return retryUntilValid(() -> { + List names = FileReaderService.readFile(dir); + List crews = new ArrayList<>(); + for (String name : names) { + crews.add(Crew.from(course, name)); + } + return crews; + }); } private InputInformation readCourseAndLevelAndMission() { - return InputParser.parseCourseAndLevelAndMission(inputView.readCourseAndLevelAndMission()); + return retryUntilValid(() -> + InputParser.parseCourseAndLevelAndMission(inputView.readCourseAndLevelAndMission()) + ); } private void handlePairMatching(Result result, InputInformation information, Crews crews) { @@ -89,4 +97,14 @@ private void handlePrintPairMatching(Result result, InputInformation courseAndLe outputView.printPairMatching(pairs); } + private T retryUntilValid(Supplier supplier) { + while (true) { + try { + return supplier.get(); + } catch (IllegalArgumentException e) { + outputView.printErrorMsg(e.getMessage()); + } + } + } + } diff --git a/src/main/java/pairmatching/service/InputParser.java b/src/main/java/pairmatching/service/InputParser.java index 9428559fd..dd97b316e 100644 --- a/src/main/java/pairmatching/service/InputParser.java +++ b/src/main/java/pairmatching/service/InputParser.java @@ -8,8 +8,12 @@ private InputParser() { } public static InputInformation parseCourseAndLevelAndMission(String input) { - String[] split = input.split(","); - return InputInformation.from(split[0], split[1], split[2]); + try { + String[] split = input.split(","); + return InputInformation.from(split[0], split[1], split[2]); + } catch (Exception e) { + throw new IllegalArgumentException("잘못된 입력입니다. 다시 입력해주세요."); + } } } diff --git a/src/main/java/pairmatching/view/OutputView.java b/src/main/java/pairmatching/view/OutputView.java index 661c02c08..449cd3445 100644 --- a/src/main/java/pairmatching/view/OutputView.java +++ b/src/main/java/pairmatching/view/OutputView.java @@ -5,6 +5,10 @@ public class OutputView { + public void printErrorMsg(String msg) { + System.out.println("[ERROR] " + msg); + } + public void printPairMatching(List> pairs) { System.out.println(); if (pairs == null) { From 4f2659d50eeb0804d079c3418885424f7cec9328 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 23:49:22 +0900 Subject: [PATCH 27/30] =?UTF-8?q?fix:=20=ED=99=80=EC=88=98=EB=AA=85=20cour?= =?UTF-8?q?se=20crew=EC=97=90=EC=84=9C=20null=20point=20=EC=A0=91=EA=B7=BC?= =?UTF-8?q?=ED=95=98=EC=A7=80=20=EC=95=8A=EB=8F=84=EB=A1=9D=20=EB=B3=80?= =?UTF-8?q?=EA=B2=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/pairmatching/controller/Controller.java | 1 + src/main/java/pairmatching/model/Crews.java | 4 ++-- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index ffaffde95..be9fd4cd8 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -42,6 +42,7 @@ public void run() { if ("1".equals(function)) { InputInformation courseAndLevelAndMission = readCourseAndLevelAndMission(); handlePairMatching(result, courseAndLevelAndMission, crews); + handlePrintPairMatching(result, courseAndLevelAndMission); } if ("2".equals(function)) { InputInformation courseAndLevelAndMission = readCourseAndLevelAndMission(); diff --git a/src/main/java/pairmatching/model/Crews.java b/src/main/java/pairmatching/model/Crews.java index cd3802694..3ecf55bb8 100644 --- a/src/main/java/pairmatching/model/Crews.java +++ b/src/main/java/pairmatching/model/Crews.java @@ -27,10 +27,10 @@ public List> pairMatching(Course course) { private List> makePair(List crewNames) { List> pairs = new ArrayList<>(); - for (int i = 0; i < crewNames.size(); i += 2) { + for (int i = 1; i < crewNames.size(); i += 2) { List pair = new ArrayList<>(); + pair.add(crewNames.get(i - 1)); pair.add(crewNames.get(i)); - pair.add(crewNames.get(i + 1)); pairs.add(pair); } From eabf087b1a8380a7ea1e4715a9aacb6b376561ff Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 23:51:49 +0900 Subject: [PATCH 28/30] =?UTF-8?q?feat:=20=EC=B4=88=EA=B8=B0=ED=99=94=20?= =?UTF-8?q?=EB=AC=B8=EA=B5=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/pairmatching/controller/Controller.java | 3 ++- src/main/java/pairmatching/view/OutputView.java | 6 ++++++ 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index be9fd4cd8..d85fd0a13 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -36,9 +36,10 @@ public void run() { while (!"Q".equals(function = inputView.readFunctionSelect())) { if ("3".equals(function)) { result = Result.init(); + outputView.printInitMsg(); continue; } - + if ("1".equals(function)) { InputInformation courseAndLevelAndMission = readCourseAndLevelAndMission(); handlePairMatching(result, courseAndLevelAndMission, crews); diff --git a/src/main/java/pairmatching/view/OutputView.java b/src/main/java/pairmatching/view/OutputView.java index 449cd3445..00e400e0c 100644 --- a/src/main/java/pairmatching/view/OutputView.java +++ b/src/main/java/pairmatching/view/OutputView.java @@ -9,6 +9,12 @@ public void printErrorMsg(String msg) { System.out.println("[ERROR] " + msg); } + public void printInitMsg() { + System.out.println(); + System.out.println("초기화 되었습니다."); + System.out.println(); + } + public void printPairMatching(List> pairs) { System.out.println(); if (pairs == null) { From f248a3fb517150902b4034f07da90b7e491c0947 Mon Sep 17 00:00:00 2001 From: kangrae Date: Mon, 5 Jan 2026 23:56:59 +0900 Subject: [PATCH 29/30] =?UTF-8?q?feat:=20=EC=9E=98=EB=AA=BB=EB=90=9C=20?= =?UTF-8?q?=EB=84=A4=20Or=20=EC=95=84=EB=8B=88=EC=98=A4=20=EB=AC=B8?= =?UTF-8?q?=EA=B5=AC=20=EC=9E=AC=EC=9E=85=EB=A0=A5=20=EB=A1=9C=EC=A7=81=20?= =?UTF-8?q?=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/pairmatching/controller/Controller.java | 8 +++++++- src/main/java/pairmatching/service/InputParser.java | 7 +++++++ 2 files changed, 14 insertions(+), 1 deletion(-) diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index d85fd0a13..04f3362cb 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -72,7 +72,7 @@ private InputInformation readCourseAndLevelAndMission() { private void handlePairMatching(Result result, InputInformation information, Crews crews) { // 이미 생성된 정보가 있을 때 if (result.isExist(information)) { - String rematching = inputView.readRematching(); + String rematching = readRematching(); if ("아니오".equals(rematching)) { return; } @@ -94,6 +94,12 @@ private void handlePairMatching(Result result, InputInformation information, Cre throw new IllegalArgumentException("3회 시도까지 매칭이 되지 않았습니다."); } + private String readRematching() { + return retryUntilValid(() -> + InputParser.parseYesOrNo(inputView.readRematching()) + ); + } + private void handlePrintPairMatching(Result result, InputInformation courseAndLevelAndMission) { List> pairs = result.getPairs(courseAndLevelAndMission); outputView.printPairMatching(pairs); diff --git a/src/main/java/pairmatching/service/InputParser.java b/src/main/java/pairmatching/service/InputParser.java index dd97b316e..c14c13704 100644 --- a/src/main/java/pairmatching/service/InputParser.java +++ b/src/main/java/pairmatching/service/InputParser.java @@ -16,4 +16,11 @@ public static InputInformation parseCourseAndLevelAndMission(String input) { } } + public static String parseYesOrNo(String input) { + if ("네".equals(input.trim()) || "아니오".equals(input.trim())) { + return input.trim(); + } + throw new IllegalArgumentException("네 또는 아니오로 입력해주세요."); + } + } From f2f913097f755e3cf436734fe4da2e535e33c92a Mon Sep 17 00:00:00 2001 From: kangrae Date: Tue, 6 Jan 2026 00:07:03 +0900 Subject: [PATCH 30/30] =?UTF-8?q?fix:=20=EB=8B=A4=EC=8B=9C=20=EB=A7=A4?= =?UTF-8?q?=EC=B9=AD=ED=95=98=EC=A7=80=20=EC=95=8A=EC=9D=84=20=EB=95=8C=20?= =?UTF-8?q?=EA=B3=BC=EC=A0=95=20=EB=A0=88=EB=B2=A8=20=EB=AF=B8=EC=85=98?= =?UTF-8?q?=EC=9D=84=20=EC=84=A0=ED=83=9D=ED=95=98=EB=8A=94=20=EA=B3=B3?= =?UTF-8?q?=EC=97=90=EC=84=9C=20=EC=9E=AC=EC=9E=85=EB=A0=A5=20=EB=B0=9B?= =?UTF-8?q?=EB=8A=94=20=EB=A1=9C=EC=A7=81=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pairmatching/controller/Controller.java | 17 +++++++++++++---- 1 file changed, 13 insertions(+), 4 deletions(-) diff --git a/src/main/java/pairmatching/controller/Controller.java b/src/main/java/pairmatching/controller/Controller.java index 04f3362cb..e564d5c75 100644 --- a/src/main/java/pairmatching/controller/Controller.java +++ b/src/main/java/pairmatching/controller/Controller.java @@ -41,9 +41,7 @@ public void run() { } if ("1".equals(function)) { - InputInformation courseAndLevelAndMission = readCourseAndLevelAndMission(); - handlePairMatching(result, courseAndLevelAndMission, crews); - handlePrintPairMatching(result, courseAndLevelAndMission); + handlePairMatchingProcess(result, crews); } if ("2".equals(function)) { InputInformation courseAndLevelAndMission = readCourseAndLevelAndMission(); @@ -69,12 +67,21 @@ private InputInformation readCourseAndLevelAndMission() { ); } + private Object handlePairMatchingProcess(Result result, Crews crews) { + return retryUntilValid(() -> { + InputInformation courseAndLevelAndMission = readCourseAndLevelAndMission(); + handlePairMatching(result, courseAndLevelAndMission, crews); + handlePrintPairMatching(result, courseAndLevelAndMission); + return null; + }); + } + private void handlePairMatching(Result result, InputInformation information, Crews crews) { // 이미 생성된 정보가 있을 때 if (result.isExist(information)) { String rematching = readRematching(); if ("아니오".equals(rematching)) { - return; + throw new IllegalStateException(); } } @@ -111,6 +118,8 @@ private T retryUntilValid(Supplier supplier) { return supplier.get(); } catch (IllegalArgumentException e) { outputView.printErrorMsg(e.getMessage()); + } catch (IllegalStateException e) { + continue; } } }