1๋จ๊ณ ํผ๋๋ฐฑ
๊ฐ์ฒด์ธ Controller
LottoFactory๋ฅผ ์ธ์คํด์ค ๋ณ์๋ก ๋์ง ์์๋ ์ด์ ๋
Controller๋ ๊ฐ์ฒด๊ฐ ์๋๋ผ ๋ฐ์ดํฐ๋ฅผ ๊ฐ์ง๋ฉด ์๋๋ค๊ณ ์๊ฐํ๊ณ ์์๋ค.
๋น์ฐํ Domain๋ง ๊ฐ์ฒด๋ผ๊ณ ์๊ฐํ์๋ค. (๋ชจ๋ฅด๋๊ฑด ๋ถ๋๋ฌ์ด๊ฒ ์๋๋ค ๐ฅฒ)
ํ์ง๋ง ์๊ฐํด๋ณด๋ Controller๋ ๋๋ฉ์ธ๊ณผ ๋ทฐ๋ฅผ ์ด์ด์ฃผ๋ ๋์์, ๊ฐ์ฒด๋ฅผ ์์ฑํ๋ ์ฑ
์์ด ์๋ค.
์ธ์คํด์ค ๋ณ์๋ก ๊ฐ์ง๊ณ ์๊ฒ ๋๋ค๋ฉด getLottoTickets ๋ฉ์๋์์ ๋งค๋ฒ ๊ฐ์ฒด๋ฅผ ์์ฑํ ํ์๊ฐ ์๋ค.
์ผ๋จ ์ด ์ฝ๋์์ ์ค์ํ ์ ์ ์ด์ฐจํผ ์ง๊ธ ๋ก๋๋ฅผ ์์ฑํ๋ ์ฑ
์์ ์ปจํธ๋กค๋ฌ์์ ํ๊ณ ์์์ผ๋
โ๋ถํ์ํ ๊ฐ์ฒด ์์ฑ์ ๋ฐฉ์งํ๋๋ก ์ธ์คํด์ค ๋ณ์๋ก๋ง๋ค์ด์ ์ฌํ์ฉํ์โ๊ฐ ๋ชฉ์ ์ด๋ค.
- ๋ฐ์ํ ์ปค๋ฐ
๋ฐ๋ณต๋๋ ์์ ์ฒ๋ฆฌ
๋ฏธ์
๋ฐ๋๋ผ์ธ์ ๋ง์ถ๊ธฐ ์ํด ์ข ๋ ๊ผผ๊ผผํ ํ์ธ์ ๋ชปํ๋ ๋ถ๋ถ์ธ๋ฐ,
๋ก๋ ํฐ์ผ์ ๋ง๋๋ LottoTicketFactory์ ์๋ ์์ ๊ฐ๋ค์ด LottoNumber๋ LottoTicket๋ฑ ์ฌ๋ฌ ๊ณณ์์ ์ค๋ณต๋์ด ์ฐ์ด๊ณ ์์๋ค.
๋ ์ฌ์ง์ด ๋ก๋์ MAX ๋ฒํธ๋ 45์ธ๋ฐ, 49๊น์ง๋ก ์
๋ ฅํด ๋์๋ค ๐
๋๋ถ์ ์์๊ฐ ํ๋๋ผ๋ ๊ผผ๊ผผํ ํ์ธํด์ผ๊ฒ ๋ค๋ ๊นจ๋ฌ์์ ์ป์๋ค.
์ค๋ณต๋๋ ์์๋ฅผ ๋ง์ผ๋ฉฐ, ๊ฐ ๊ฐ์ฒด๊ฐ ์๊ณ ์์ด์ผ ํ๋ ๊ฐ๋๋ก ์์๋ฅผ ๋๊ณ
์ด๋ฅผ import ํด์ ์ฌ์ฉํ๋๋ก ์์ ํ๋ค.
LottoNumber
public class LottoNumber implements Comparable<LottoNumber> {
public static final int MIN_LOTTO_NUMBER = 1;
public static final int MAX_LOTTO_NUMBER = 45;
private static final Pattern NUMBER_PATTERN = Pattern.compile("^[0-9]*$");
LottoTicket
public class LottoTicket {
public static final int LOTTO_TICKET_SIZE = 6;
LottoFactory
import static lotto.domain.LottoNumber.MAX_LOTTO_NUMBER;
import static lotto.domain.LottoNumber.MIN_LOTTO_NUMBER;
import static lotto.domain.LottoTicket.LOTTO_TICKET_SIZE;
import static lotto.domain.Money.LOTTO_PRICE;
public class LottoTicketFactory {
private static final int START_INDEX = 0;
- ๋ฐ์ํ ์ปค๋ฐ
๊ตฌ๋งค ๊ธ์ก ๊ณ์ฐ ๋ฒ
๋ฆฌํฉํ ๋ง ์ ๋ก์ง์ผ๋ก๋ ๊ตฌ๋งค ๊ธ์ก์ ์
๋ ฅ ๋ฐ์ ๋ ๋ง์ฝ 14500์์ด ๋ค์ด์ค๋ฉด ์ฌ์ฉํ ๊ธ์ก์
14์ฅ์ ์ฌ๋๋ฐ 14000์๋ง ๋ค๊ฒ ํ๊ณ 500์์ด ๋จ๋ ๊ฒ์ ์์ธ๋ผ๊ณ ์๊ฐํ์ง ์๊ณ ์งํํ๋ค.
๊ทธ๋ฐ๋ฐ ์ด ๋ก์ง์ ๊ตฌ๋งคํ ๊ธ์ก์ด ์๋ ์ง๋ถํ 14500์์ผ๋ก ์์ต๋ฅ ์ ๊ณ์ฐํ๊ณ ์๋ค.
๋๋ฌธ์ ์
๋ ฅ ๊ธ์ก๊ณผ ๊ตฌ๋งค ๊ธ์ก์ ๋ฏธ์ผ์น ์ค๋ฅ๊ฐ ๋ฐ์ํ๋ค.
ํผ๋๋ฐฑ์ ํตํด lottoResult์์ ๊ตฌํ ์ ์๋ ํฐ์ผ ๊ฐ์์ ์์ ๋ณ์์ธ ๋ก๋์ ๊ตฌ๋งค์ฅ์๋ก
์ง๋ถ ๊ธ์ก์ ๊ตฌํ ์ ์์์ ๊นจ๋ซ๊ณ showResult()
์์ money
๋ฅผ ๋งค๊ฐ๋ณ์๋ก ๋ฐ์ ํ์๊ฐ ์์์ ๊นจ๋ฌ์๋ค.
๋๋ถ์ money์์ ์ฐ๊ด๊ด๊ณ๋ฅผ ํ๋ ๋์ ์ ์๊ณ ,
์์ต๊ธ ๊ณ์ฐ ์ ์
๋ ฅ ๊ธ์ก๊ณผ ๊ตฌ๋งค ๊ธ์ก ๋ฏธ์ผ์น๋ก ์ธํ ์์ต๋ฅ ์๋ฌ๋ฅผ ๋ฐฉ์งํ ์ ์๋ค.
Prize์์์ static ๋ฉ์๋ ์ฌ์ฉ
๋ฆฌํฉํ ๋ง ์ Prize
public static Prize getPrizeType(int matchCount, boolean isBonusBall) {
if (isMatchCountEqualsPivot(matchCount) && isBonusBall) {
return SECOND_PRIZE;
}
return Arrays.stream(values())
.filter(s -> s.matchCount == matchCount)
.findFirst()
.orElse(NO_PRIZE);
}
private static boolean isMatchCountEqualsPivot(int matchCount) {
return matchCount == BONUS_CHECK_PIVOT;
}
public static double calculatePrizeMoneySum(List<Prize> lottoResults, Money money) {
Money moneySum = Money.ZERO;
for (Prize prize : Prize.values()) {
Money perPrizeMoneySum = prize.prizeMoney
.multiple(getCountByPrizeType(lottoResults, prize));
moneySum = moneySum.plus(perPrizeMoneySum);
}
return moneySum.getRate(money);
}
public static int getCountByPrizeType(List<Prize> lottoResults, Prize prize) {
return (int) lottoResults.stream()
.filter(p -> p.equals(prize))
.count();
}
๋ฆฌํฉํ ๋ง ์ LottoResult
public class LottoResult {
private final List<Prize> lottoResults;
public LottoResult(List<Prize> lottoResults) {
this.lottoResults = new ArrayList<>(lottoResults);
}
public double calculateProfitRate(Money money) {
return Prize.calculatePrizeMoneySum(lottoResults, money);
}
public int getCountPerPrizeType(Prize prize) {
return Prize.getCountByPrizeType(lottoResults,prize);
}
}
LottoResult์์ calculateProfitRate()
์ ํ๊ธฐ ์ํด Prize์ ๋์์ ๋ฐ์๋ค.
lottoResults๊ฐ Prize์ ๋์์ ๋ฐ์ง ์๊ณ List<Prize> lottoResults
๊ฐ๊ฐ์ prize์๊ฒ ๋ฉ์์ง๋ฅผ ๋ณด๋ด ์ค์ค๋ก ๊ณ์ฐํ ์ ์๋๋ก ์ฝ๋๋ฅผ ๋ค์๊ณผ ๊ฐ์ด ์์ ํ์๋ค.
LottoResult
public Money getTotalProfit() {
Money totalProfit = Money.ZERO;
for (Prize prize : lottoResults) {
totalProfit = totalProfit.plus(prize.getPrizeMoney());
}
return totalProfit;
}
ํ์ง๋ง ๋ฆฌํฉํ ๋ง ํ์๋ ์์ง ๊ฐ์ฒด ์ค์ค๋ก ํ ์ ์๋์ผ๋ค์ด ๋จ์์์๋ค.
๋ ์ด๋๊น์ง ๋ก๋ ํฐ์ผ๊ณผ ๋น์ฒจ ํฐ์ผ์ ๋น๊ตํด ๊ฒฐ๊ณผ๋ฅผ ๋ฐํํ๋ ์ฑ
์์
lott. Tickets๊ฐ ๊ฐ์ง๊ณ ์์๋ค.
๊ณฐ๊ณฐํ ์๊ฐํด๋ณด๋ ๋ก๋ ํฐ์ผ๊ณผ ๋น์ฒจ ํฐ์ผ์ ๋น๊ตํด ๊ฒฐ๊ณผ๋ฅผ ๋ฐํํ๋ ์ฑ
์์ winningLotto๊ฐ ๋งก๋ ๊ฒ์ด ๋ ์ ํฉํ๋ค๊ณ ํ๋จ์ด ๋์๊ณ ,
winningLotto์์ prize๋ฅผ ์ฒดํฌํ๋๋ก ์ฑ
์์ ์ด๋ํ์๋ค.
์ต์ข
์ ์ผ๋ก LottoResult๋ฅผ ๋ฐํํ๋ ๊ฒ์ winnigLotto์์ ๋ด๋นํ๋ฉฐ,
๋ Prize์ ๋์์ ๋ฐ์ง ์๊ณ ์ค์ค๋ก prize๋ฅผ ์ฒดํฌํ๋๋ก ํ์๋ค.
๋ฆฌํฉํ ๋งํ WinnigLotto์ ๋ฉ์๋ ์ผ๋ถ
public Prize matchPrize(LottoTicket lottoTicket) {
int matchCount = getMatchingCount(lottoTicket);
boolean isBonusNumber = isContainBonusNumber(lottoTicket);
return Prize.findPrize(matchCount, isBonusNumber);
}
private int getMatchingCount(LottoTicket lottoTicket) {
return (int) lottoTicket.lottoTicket().stream()
.filter(winningTicket.lottoTicket()::contains)
.count();
}
private boolean isContainBonusNumber(LottoTicket lottoTicket) {
return lottoTicket.lottoTicket()
.stream()
.anyMatch(lottoNumber -> lottoNumber.equals(bonusNumber));
}
๋ฆฌํฉํ ๋ง ํ Prize์์ ์ค์ด๋ static ๋ฉ์๋๋ค
public static Prize findPrize(int matchCount, boolean isBonusNumber) {
if (isMatchCountEqualsPivot(matchCount) && isBonusNumber) {
return SECOND_PRIZE;
}
return Arrays.stream(values())
.filter(s -> s.matchCount == matchCount)
.findFirst()
.orElse(NO_PRIZE);
}
private static boolean isMatchCountEqualsPivot(int matchCount) {
return matchCount == BONUS_CHECK_PIVOT;
}
public Money getPrizeMoney() {
return prizeMoney;
}
public int getMatchCount() {
return matchCount;
}
collectingAndThen
๋ฆฌ๋ทฐ์ด๋๊ป์ ์์ ํด์ฃผ์ ์ฝ๋๋ collectingAndThen
๋ฉ์๋๋ฅผ ์ฌ์ฉํ๋๋ฐ,
์ฒ์๋ณด๋ ๋ฉ์๋๋ผ ์ฐพ์๋ณด๋ collecting์ ์งํํ ํ ๊ทธ ๊ฒฐ๊ณผ๋ก ๋ฉ์๋๋ฅผ ํธ์ถํ ์ ์๋ ๋ฉ์๋ ์๋ค.
stream map์ ์จ์ ๊ฐ์ฒด ํ๋ํ๋๋ฅผ ์์ฑํ๊ณ ์ด๋ฅผ ๋ฆฌ์คํธ๋ก ๋ฐ๊ฟ,
๋ ๊ฐ์ฒด๋ฅผ ์์ฑํ๋ ๋์ ๋ก์ง์์ ์ด ๋ฉ์๋๋ฅผ ์ฌ์ฉํ๋ฉด
์ข ๋ ๊ฐ๊ฒฐํ๊ฒ ํํํ ์ ์์๋ค.
์ฌ์ฉ๋ฒ์ ๋ฐฐ์ ์ผ๋, ์์ผ๋ก ์์ฃผ ์ฌ์ฉํ ๊ฒ์ด๋ค ๐
๋ Collections์ ๋ค์ํ API๋ฅผ ์ดํด๋ณด์์ผ๊ฒ ๋ค.
2๋จ๊ณ ์ด๊ธฐ ๋ฆฌํฉํ ๋ง
LottoCount ๊ฐ์ฒด ์ถ๊ฐ
์ด๋ฒ ๋ฆฌํฉํ ๋ง์์ ์๋ ๋ก๋ ๊ฐ์
๋ฅผ ์
๋ ฅ ๋ฐ๊ณ , ์ด ๊ฐฏ์ ๋งํผ ๋ก๋๋ฅผ ์์ฑํ๊ณ ์ถ๋ ฅํด์ผํ๋ค.
์์๊ฐ ํฌ์ฅ์ ์๋ฏธ๋ ๋ด์ผ๋ฉด์ ์
๋ ฅ ๋ฐ๋ ์๋ ๋ก๋ ๊ฐฏ์์ ๋ํ ๊ฒ์ฆํ๊ณ ,
์ด์ ๋ํ ์ํ์ ํ์๋ฅผ ํ ๊ณณ์์ ๊ด๋ฆฌ ํ๊ธฐ ์ํด LottoCount
๊ฐ์ฒด๋ฅผ ๋ง๋ค๊ฒ ๋์๋ค.
public class LottoCount {
private final int manualCount;
private final int autoCount;
public LottoCount(int manualCount, int totalCount) {
validateLottoCount(manualCount, totalCount);
this.manualCount = manualCount;
this.autoCount = totalCount - this.manualCount;
}
private void validateLottoCount(int manualCount, int totalCount) {
if (manualCount > totalCount || manualCount < 0) {
throw new IllegalArgumentException("[ERROR] ๊ตฌ๋งค ๊ฐ๋ฅํ ๋ก๋ ๊ฐ์ ๋ฒ์๊ฐ ์๋๋๋ค.");
}
}
public int getManualCount() {
return manualCount;
}
public int getAutoCount() {
return autoCount;
}
}
Exception
ํ์์ผ ๊ฐ์์ธ Exception์ด ๋ด๊ฒ๋ ๋ง์ ๋ฐฐ์์ ์ฃผ์ด์,
์ด๋ฒ ์๊ตฌ์ฌํญ์ธ ์ฌ์ฉ์ ์
๋ ฅ๊ฐ์ ๋ํ ์์ธ์ฒ๋ฆฌ๋ฅผ ์ ๊ฒฝ์ผ๋ค.
์ด์ ์๋ Custom Exception์ ๋ง๋ค์ด์ ๊ฐ ๊ฐ์ฒด๋ง๋ค ์์ธ ์ฒ๋ฆฌ๋ฅผ ํด์ฃผ์์ผ๋,
- ๋ฆฌํฉํ ๋ง ์ Custom Class ```java package lotto.exception;
import lotto.view.ErrorView;
public class IllegalMoneyException extends IllegalArgumentException { public IllegalMoneyException() { ErrorView.printIllegalMoneyErrorMessage(); } }
๊ฐ Custom Exception ํด๋์ค๊ฐ ๋ฐ๋ก ์ฒ๋ฆฌํ๋ ์ผ์ด ์๊ณ ,
๋ฉ์ธ์ง๋ super์๊ฒ ์ ๋ฌํ๋ ๊ฒ์ด ์๋ `ErrorView`๋ผ๋ ๊ฐ์ฒด๋ฅผ ํตํด ์ถ๋ ฅํ๊ณ ์๊ธฐ ๋๋ฌธ์
ํ์์ฑ์ ๋ชป๋๋ผ๊ฒ ๋์ด ์๋ฐ์ ๊ธฐ๋ณธ ์์ธ๋ฅผ ์ฌ์ฉํ๋๋ก ๋ฆฌํฉํ ๋ง์ ์งํํ๋ค.
๋ ๊ฐ์ฒด ๋จ์๋ก ๋ฌถ์ด์ ์๋ฌ ๋ฉ์ธ์ง๋ฅผ ๋ณด๋ด๋ ๋ถ๋ถ์
๊ฐ ์์ธ ์ฌํญ์ ๋ง๊ฒ ์๋ฌ ๋ฉ์์ง๋ฅผ ๋ณด๋ด๋๋ก ์์ ํ๋ค.
#### LottoTicketFactory -> AutoNumbersFactory
์๊ตฌ์ฌํญ์ ๋ฐ๋ผ ๋ฆฌํฉํ ๋ง์ ์งํํ๋ฉด์ `LottoTickets`๋ฅผ ์์ฑํด๋ด๋ LottoTicketfactory์ ์ญํ ์ ๋ํ ์๋ฌธ์ด ๋ค์๋ค.
์ฒ์ ๋ฆฌํฉํ ๋ง์์๋ ๊ฐ์ฒด๋ฅผ ๋ง์ด ๋ณ๊ฒฝํ์ง ์๊ธฐ ์ํด ์๋ ๋ก๋ ๋ฒํธ๋ค์ ๋ฐ๊ณ ์๋ ๋ก๋ ๊ฐฏ์๋ฅผ ๋ฐ์์
`LottoTicketFactory`์์ ์๋ ๋ก๋ ์ซ์๋ค์ ๋ง๋ค๊ณ `LottoTickets`๋ฅผ ์์ฑํ๋ ์ญํ ๋ก ์งํํ๋๋ฐ,
๋ก๋ ํฐ์ผ๋ค ๊ฐ์ฒด๋ฅผ ์์ฑํ๊ธฐ ์ํด ๋ ๋ค๋ฅธ `LottoTicketFactory`๋ฅผ ์์ฑํ๋ ๊ฒ์ด ์ข์ง ๋ชปํ ๋ฐฉ์์ด๋ผ๋ ์๊ฐ์ด ๋ค์๋ค.
๋๋ฌธ์ LottoTickets ๊ฐ์ฒด๋ฅผ ์์ฑํ ๋ ๋ก๋ ๋ฒํธ๋ค์ ๋ฆฌ์คํธ๋ค์ ๋ฐ์์
(`List<List<LottoNumber>> lottoNumbersGroup`) `LottoTickets` ์์์ ๋ก๋ ํฐ์ผ๋ค์ ์์ฑํ๋ ๋ฐฉ์์ผ๋ก ๋ณ๊ฒฝํ๋ค.
๊ทธ๋ฆฌ๊ณ ๊ธฐ์กด `LottoTicketFactory`๋ `AutoNumbersFactory`๋ก ๋ณ๊ฒฝํ์ฌ
์๋ ๋ก๋ ์ซ์ ๋ฆฌ์คํธ๋ฅผ ๋ง๋ค์ด๋ด๋ ์ญํ ๋ก ๋ณ๊ฒฝํด๋ณด์๋ค !
#### LottoNumber
0223 ์์
๋ ๋ก๋ ๋๋ฒ์ ๋ฒ์์ ์ ํ์ด ์์ผ๋, ์ด๋ฅผ ๋ฏธ๋ฆฌ ์บ์ฑํด์ ์ฌ์ฉํ๋ ๋ฐฉ๋ฒ์ ์๊ฐํด๋ณด๋ผ๊ณ ํ์
จ๋ค.
์๊ฐ์ ํด๋ณด๊ณ ์บ์ฑํ๋ ๋ฐฉ๋ฒ์ ์ฐพ์๋ณด๋ `HashMap`์ ์ด์ฉํด์ ์บ์ฑ์ ๊ตฌํํ ์ ์์์ ๊นจ๋ฌ์๋ค.
์ด๋ก ์์ฑ์๋ฅผ `private`๋ก ๋ง์ ๋ถํ์ํ ๊ฐ์ฒด ์์ฑ์ ๋ง๊ณ ,
`static block`์ ์ํด ๋ฏธ๋ฆฌ ์บ์ฑ๋ `LottoNumber`์์ ํค๊ฐ์ผ๋ก ์ ๊ทผํด ํด๋น ๋ก๋๋๋ฒ๋ฅผ ๊ฐ์ ธ์ค๋ ํ์์ผ๋ก ๋ฆฌํฉํ ๋ง์ ์งํํ๋ค.
* LottoNumber ์บ์ ์ ์ฉ ๋ถ๋ถ
```java
static {
IntStream.range(MIN_LOTTO_NUMBER, MAX_LOTTO_NUMBER + 1)
.forEach(i -> CACHE_LOTTO_NUMBERS.put(i, new LottoNumber(i)));
}
public static LottoNumber valueOf(int index) {
validateLottoNumber(index);
return CACHE_LOTTO_NUMBERS.get(index);
}
2๋จ๊ณ ํผ๋๋ฐฑ
์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋
์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋์ ๋ํด ์ ๋ฆฌ๋ ํ์์ผ๋,
์ฌ์ค ์ธ์ ์จ์ผํ๊ณ ์ธ์ ์ฐ์ง ๋ง์์ผํ ์ง ์์ง ๊ฐ์ด ์์๋ค ํด์ผํ๋ ๐ฅฒ
๊ทธ๋ฐ๋ฐ ํฌ๋ฃจ๋ค์ด๋ ์๊ธฐ๋ฅผ ํด๋ณด๋,
์ ๋ต์ ์์ผ๋ ์์ ์ด ์ฐ๋ ๋ช
๋ถ์ ๊ฐ์ง๋๊ฒ ์ข์ ๊ฒ ๊ฐ๋ค๋ ๊ฒฐ๋ก ์ ๋ด๋ ธ๋ค.
์ฌ์ค ์ด๋๊น์ง ์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋์ ์ฌ์ฉ์ฑ์ ์ ๋๋ก ์ธ์งํ์ง ๋ชปํ๊ณ ์์๋ ๊ฒ ๊ฐ๋ค.
static์ด๋ผ๋ ๋ช
๋ถ ๋๋ฌธ์ ๊ฐ์ฒด๋ฅผ ๊ณต์ ํ๋ค๊ณ ์๊ฐํ์ผ๋,
์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋ ๋ด์์ ์๋ก์ด ๊ฐ์ฒด๋ฅผ ์์ฑํด ๋ฐํํ๋ค๋ฉด
์ํ๋ฅผ ๊ณต์ ํ์ง ์๋ ๊ฒ์ด๋ค.
์ static์ด๋ผ๋ ๋ช
๋ชฉ ๋๋ฌธ์ ์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋๊ฐ ๋ฌด์กฐ๊ฑด
๊ณต์ ๋๋ ๊ฐ์ฒด๋ฅผ ๋ง๋ ๋ค๊ณ ๋ง ์๊ฐํ์๊น ๐ฅฒ
๋๋ฌธ์ ์ด๋ฒ ๋ฆฌํฉํ ๋ง์์๋ ์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋๋ฅผ ์ ๊ทน ์ฌ์ฉํด ๋ณด์๋ค.
๋ง์ ์ฑ ์์ ์ง๊ณ ์๋ LottoController
์ด ๋น์ ๋ด๊ฐ ๊ตฌํํ LottoController๋
private LottoTickets buyLottoTickets(LottoCount lottoCount) {
List<List<LottoNumber>> lottoNumbersGroup = new ArrayList<>();
lottoNumbersGroup.addAll(createAllManualLottoTicket(lottoCount.getManualLottoCount()));
lottoNumbersGroup.addAll(createAutoNumbers(lottoCount.getAutoLottoCount()));
return new LottoTickets(lottoNumbersGroup);
}
์ด๋ฐ์์ผ๋ก LottoTicket์ ํด๋นํ๋ List<LottoNumber>
๋ Controller์์ ๋ง๋ค๊ณ ,
์ด๋ฅผ ๊ฐ์ง๊ณ LottoTickets๊น์ง ๋ง๋ค์ด ๋ธ๋ค.
๋ ๋ณด๋ค์ถ์ด List<List<LottoNumber>>
๋ฅผ ๋ง๋ค์ด ๋ด๊ธฐ ์ํด ๋ณต์กํ ์ฝ๋๋ฅผ ๊ฐ์ง๊ณ ์์๋ค.
private List<List<LottoNumber>> createAllManualLottoTicket(int manualLottoCount) {
OutputView.printInputManualLottoNumbers();
return IntStream.range(0, manualLottoCount)
.mapToObj(i -> InputView.inputNumbers()
.stream()
.map(input -> LottoNumber.valueOf(ParseUtil.parseInt(input)))
.collect(Collectors.toList()))
.collect(Collectors.toList());
}
์ด์ ๋ํด ๋จ๊ฒจ์ฃผ์ ํผ๋๋ฐฑ์ ๋ค์๊ณผ ๊ฐ๋ค.
์ด๋ก ์ธํด ์ ๋ฐ์ ์ผ๋ก ๋ง์ ์์ ์ด ์ผ์ด๋ฌ๋ค.
LottoTicket์ auto()
, manual()
์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋๋ฅผ ๋ง๋ค๊ณ ,
LottoTickets์๋ auto()
์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋๋ฅผ ๋ง๋ค์ด
LottoController์์ ์์ฑํ๊ณ ์๋ ์ฑ
์์ ๋ถ๋ฐฐํ๋ค.
LottoTicket - auto(), manual()
public static LottoTicket auto() {
return new LottoTicket(LottoNumbersFactory.generateAutoLottoNumbers());
}
public static LottoTicket manual(List<String> lottoNumberStrings) {
return lottoNumberStrings.stream()
.map(i -> LottoNumber.valueOf(ParseUtil.parseInt(i)))
.collect(collectingAndThen(toList(), LottoTicket::new));
}
LottoTicket์์ List<String>
์ ๋ฐ์ ์๋ ๋ก๋ ํฐ์ผ์ ์์ฑํ๋๋ก ๋ฆฌํฉํ ๋ง ํด๋ณด์๋ค !
LottoTickets - auto()
public static LottoTickets auto(int count) {
return Stream.generate(LottoTicket::auto)
.limit(count)
.collect(collectingAndThen(toList(), LottoTickets::new));
}
๋๋ถ์ LottoContoller์ ์๋ ๋ง์ ์ฑ ์์ด ๋ถ๋ฐฐ๋์๋ค๊ณ ์๊ฐํ๊ณ (?), ๊ฐ ๋ฉ์๋ ์ฝ๋๋ ๊ฐ๊ฒฐํด์ก๋ค๊ณ ๋๋๋ค.
LottoController ์ผ๋ถ
private LottoTickets buyLottoTickets(LottoCount lottoCount) {
LottoTickets lottoTickets = createManualLottoTickets(lottoCount.getManualCount());
lottoTickets.combine(LottoTickets.auto(lottoCount.getAutoCount()));
return lottoTickets;
}
private LottoTickets createManualLottoTickets(int manualCount) {
OutputView.printInputManualLottoNumbers();
return Stream.generate(() -> LottoTicket.manual(InputView.inputNumbers()))
.limit(manualCount)
.collect(collectingAndThen(toList(), LottoTickets::new));
}
LottoTickets
ํผ๋๋ฐฑ์ ๋ฃ๊ณ ์๊ฐํด๋ณด๋ LottoTickets๋ฅผ ๋๋ ๋จ์ํ LottoTicket์ ๋ชจ์์ด๋ผ๊ณ ๋ง ์๊ฐํ์๋ค.
(์ฝ๊ฐ Repository๋ก ์๊ฐํ๋ ๊ฒ ๊ฐ๋ค.)
๋ฆฌํํ ๋ง ์ LottoTickets
private final List<LottoTicket> lottoTickets;
public LottoTickets(List<List<LottoNumber>> lottoNumbersGroup) {
this.lottoTickets = new ArrayList<>(createLottoTickets(lottoNumbersGroup));
}
public List<LottoTicket> lottoTickets() {
return Collections.unmodifiableList(lottoTickets);
}
private List<LottoTicket> createLottoTickets(List<List<LottoNumber>> lottoNumbersGroup) {
return lottoNumbersGroup.stream()
.map(LottoTicket::new)
.collect(Collectors.toList());
}
๊ณ ๋ฏผํด๋ณด๋ ์ด์ ์ ์๋์ ๊ฐ์ด WinningTicket์์ ๋น์ฒจ ๊ฒฐ๊ณผ๋ฅผ ์ฐ์ถํ์๋๋ฐ,
๋ฆฌํํ ๋ง ์ WinnigLotto
public LottoResult checkPrizes(LottoTickets lottoTickets) {
return lottoTickets.lottoTickets().stream()
.map(this::matchPrize)
.collect(collectingAndThen(toList(), LottoResult::new));
}
public Prize matchPrize(LottoTicket lottoTicket) {
int matchCount = getMatchingCount(lottoTicket);
boolean isBonusNumber = isContainBonusNumber(lottoTicket);
return Prize.findPrize(matchCount, isBonusNumber);
}
private int getMatchingCount(LottoTicket lottoTicket) {
return (int) lottoTicket.lottoTicket().stream()
.filter(winningTicket.lottoTicket()::contains)
.count();
}
private boolean isContainBonusNumber(LottoTicket lottoTicket) {
return lottoTicket.lottoTicket()
.stream()
.anyMatch(lottoNumber -> lottoNumber.equals(bonusNumber));
}
์ด๋ ๊ฒ ๋ชจ๋ ๋ฉ์๋์์ LottoTicket์ ๊ฐ์ ๊บผ๋ด์ค๊ณ ์์๋ค.
๋๋ฌธ์ LottoTickets์ WinnigLotto๋ฅผ ์ฃผ์ด ๊ฐ LottoTicket์๊ฒ ๋น๊ตํ๋ผ๋ ๋ฉ์์ง๋ฅผ ์ฃผ๋๊ฒ์ด ๋ ์ณ๋ค๊ณ ์๊ฐํด์
LottoTickets์์ ๊ฒฐ๊ณผ๋ฅผ ๋น๊ตํ๋ ์ญํ ์ ๋ถ์ฌํ๊ฒ ๋์๋ค.
๋ Controller์์ ๋ก๋ ํฐ์ผ์ ์์ฑํ๋ ์ญํ ์ ๋๊ธฐ ์ํด ๋ฉ์๋๋ค์ด ๋ฐ๋ก LottoTickets๋ฅผ ๋ฐํํ๋๋ก ํ๋ฉด์
ManualLottoTickets
์ LottoTickets.auto
๋ฅผ์์ฑํ๋๋ฐ
์์ฑ๋ ์ด ๋ LottoTickets
๋ค์ ํฉ์น๋ ์ญํ ๋ ํ์ํ๋ค๊ณ ์๊ฐํด์
combine()
ํ ์ ์๋ ๊ธฐ๋ฅ์ ์ถ๊ฐํ๋ค.
๊ทธ๋ฐ๋ฐ WinnigLotto์ ์๋ ๊ฒ๋ค์ LottoTickets๋ก ๋ถ๋ฐฐํ๋ WinningLotto์
์ญํ ์ด ๋ค ๋นผ์๊ฒจ ๋ฒ๋ฆฐ๊ฑด ์๋๊น ๊ณ ๋ฏผ์ด ๋์์ง๋ง,
๋ฆฌ๋ทฐ์ด ๋ถ๊ป์ ๊ด์ฐฎ๋ค๊ณ ๋ง์ํด์ฃผ์ จ๋ค.
๋ฏธ์
์ ์งํํ๋ฉด ํ ์๋ก ์์ง ๋ฐฐ์ธ ๊ฒ์ด ๋ง๊ณ ๋์ ๋ถ์กฑํจ์ ๋๋๋ค.
๋ฐฐ์ธ ๊ฒ์ด ๋ง๋ค๋ ๊ฒ์ ๋๋ ์ฑ์ทจ๊ฐ์ด ๋ง๋ค๋ ๊ฒ์ด๋ ์์ผ๋ก ํ์ดํ
ํ์ ๐โโ๏ธ