Skip to content

Commit

Permalink
Merge pull request #2 from BDD-CLUB/gusah009/baseball
Browse files Browse the repository at this point in the history
[숫자 야구 게임] 미니언 미션 제출합니다.
  • Loading branch information
gusah009 authored Feb 20, 2024
2 parents 1155f76 + c8cea8e commit 0cc45d5
Show file tree
Hide file tree
Showing 6 changed files with 147 additions and 1 deletion.
6 changes: 5 additions & 1 deletion kotlin-baseball/src/main/kotlin/baseball/Application.kt
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
package baseball

import baseball.controller.BaseballController
import baseball.view.View

fun main() {
TODO("프로그램 구현")
val baseballController = BaseballController(View())
baseballController.start()
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
package baseball.controller

import baseball.model.NUMBER_LENGTH
import baseball.model.Numbers
import baseball.model.StrikeBall
import baseball.model.UserContinueGame
import baseball.view.View

class BaseballController(
private val view: View,
) {
fun start() {
view.printStartMessage()
do {
val computerNumbers = Numbers.generateRandom()
do {
val userNumbers = view.getUserNumbers()
val strikeBall = userNumbers.compare(computerNumbers)
view.printStrikeBall(strikeBall)
} while (strikeBall.isGameContinue())
view.printEndMessage()
} while (view.getUserContinueGame() == UserContinueGame.RESTART)
}

private fun StrikeBall.isGameContinue() = this.strike != NUMBER_LENGTH
}
55 changes: 55 additions & 0 deletions kotlin-baseball/src/main/kotlin/baseball/model/Numbers.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
package baseball.model

import camp.nextstep.edu.missionutils.Randoms

const val MIN_NUMBER_INCLUDE = 1
const val MAX_NUMBER_INCLUDE = 9
const val NUMBER_LENGTH = 3

data class Numbers(val numbers: List<Number>) {
companion object {
fun generateRandom() =
Numbers(
mutableListOf<Number>().apply {
while (size != NUMBER_LENGTH) {
val pickNumber = Number(Randoms.pickNumberInRange(MIN_NUMBER_INCLUDE, MAX_NUMBER_INCLUDE))
if (pickNumber !in this) {
this.add(pickNumber)
}
}
}.toList()
)
}

init {
require(numbers.size == NUMBER_LENGTH)
require(numbers.distinct().size == numbers.size)
}

fun compare(other: Numbers): StrikeBall {
val strike = getStrike(other)
val ball = getBall(other)
return StrikeBall(strike, ball)
}

fun getStrike(other: Numbers) =
(0 until NUMBER_LENGTH)
.count { this.numbers[it] == other.numbers[it] }

fun getBall(other: Numbers) =
(0 until NUMBER_LENGTH)
.count { i -> isBall(i, other) }

private fun isBall(i: Int, other: Numbers) =
(0 until NUMBER_LENGTH)
.any { j ->
if (i == j) return@any false
this.numbers[i] == other.numbers[j]
}
}

data class Number(val number: Int) {
init {
require(number in MIN_NUMBER_INCLUDE..MAX_NUMBER_INCLUDE)
}
}
17 changes: 17 additions & 0 deletions kotlin-baseball/src/main/kotlin/baseball/model/StrikeBall.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
package baseball.model

data class StrikeBall(val strike: Int, val ball: Int) {
override fun toString() =
buildString {
if (ball != 0) {
append("${ball}")
}
if (strike != 0) {
append("${strike}스트라이크 ")
}
if (strike == 0 && ball == 0) {
append("낫싱")
}
return toString()
}
}
14 changes: 14 additions & 0 deletions kotlin-baseball/src/main/kotlin/baseball/model/UserContinueGame.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
package baseball.model

enum class UserContinueGame(val value: Int) {
RESTART(1),
END(2),
;

companion object {
fun of(input: String): UserContinueGame {
return entries.find { it.value == input.toInt() }
?: throw IllegalArgumentException("Input must in $entries. input: $input")
}
}
}
30 changes: 30 additions & 0 deletions kotlin-baseball/src/main/kotlin/baseball/view/View.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
package baseball.view

import baseball.model.NUMBER_LENGTH
import baseball.model.Number
import baseball.model.Numbers
import baseball.model.StrikeBall
import baseball.model.UserContinueGame
import camp.nextstep.edu.missionutils.Console

class View {
fun printStartMessage() {
println("숫자 야구 게임을 시작합니다.")
}

fun getUserNumbers(): Numbers {
print("숫자를 입력해주세요 : ")
return Numbers(Console.readLine().map { Number(it.digitToInt()) })
}

fun getUserContinueGame() = UserContinueGame.of(Console.readLine())

fun printStrikeBall(strikeBall: StrikeBall) {
println(strikeBall)
}

fun printEndMessage() {
println("${NUMBER_LENGTH}개의 숫자를 모두 맞히셨습니다! 게임 종료")
println("게임을 새로 시작하려면 ${UserContinueGame.RESTART.value}, 종료하려면 ${UserContinueGame.END.value}를 입력하세요.")
}
}

0 comments on commit 0cc45d5

Please sign in to comment.