[내일배움캠프 3주차 (01/13)]

yeseul jang·2026년 1월 13일

내일배움캠프

목록 보기
2/32

🔎 야구 게임

Xcode command line tool을 이용해 야구게임을 만들어 보았다. 숫자를 예측해서 맞추는 게임이다 보니 사용자 입력을 readLine()로 받아와서 게임을 진행하도록 했다.
기능적으로는 잘 동작하지만 리팩토링해야할 부분이 많다.

📌 겹치지 않는 랜덤숫자 뽑기

  • 정답이 될 세가지 숫자를 뽑는 기능을 구현해보았다.
func makeRandomNumbers() -> [Int] {
    var randomNumbers = Set<Int>()
    
    while randomNumbers.count < 3 {
        randomNumbers.insert(Int.random(in: 1...9))
    }
    return Array(randomNumbers)
}
  • Set은 중복을 허용하지 않는다는 점을 이용해 값이 3개가 될때까지 뽑아주었다.
func makeRandomNumberWithZero() -> [Int] {
    var randomNumbers = Set<Int>()
    
    while randomNumbers.count < 2 {
        randomNumbers.insert(Int.random(in: 0...9))
    }
    var resultNumbers = Array(randomNumbers)
    
    while resultNumbers.count < 3 {
        let firstNum = Int.random(in: 1...9)
        if !(resultNumbers.contains(firstNum)) {
            resultNumbers.insert(firstNum, at: 0)
        }
    }
    return resultNumbers
}
  • 나머지 숫자는 0이 가능 첫번째 숫자는 0이 되면 안된다는 조건에 맞추어서도 만들어 보았다.
  • 일단 첫번째를 제외한 나머지 숫자를 위와 같이 Set으로 겹치지 않게 해준다.
  • 이미 뽑은 숫자중에 겹치지 않으면서 0을 제외한 숫자를 랜덤으로 넣어주는 로직이다.

✏️ 더 공부해 볼 점!

Int가 첫번째 숫자가 0이면 자동으로 무시하는 점을 이용하면 더 효율적인 코드가 나올 것 같아서 시도해 보고 싶다.

📌 입력받은 숫자 편집하기

func cleanNumbers(with input:String) -> [Int]? {
    let cleanedNumbers = input.split(separator: "").compactMap { Int($0) }
    
    if cleanedNumbers.count > 3 || Set(cleanedNumbers).count != 3 {
        return nil
    } else {
        return cleanedNumbers
    }
}
  • compactMap이 자동으로 숫자로 변환되지 않으면 반환하지 않아서 숫자만 받는다는 조건에 너무 잘 맞았다.
  • 그리고 후에 받은 숫자가 3개 보다 많거나 겹치는 숫자가 있다면 nil을 반환하도록 했다.

✏️ 더 공부해 볼 점!

  • 하지만 랜덤한 String 사이에 우연찮게 숫자 세 개가 들어간다면 올바른 입력으로 처리된다. 더 고민해보아야 할 것 같다.

📌 게임 실행하기

func startGame() {
    var isGameOn = true
 
    while isGameOn {
        print("✏️ 숫자를 입력하세요:", terminator: "")
        
        guard let userInput = readLine(),
              let cleanedNumbers = cleanNumbers(with: userInput) else {
            print("❌ 잘못된 입력입니다. 겹치지 않는 세자리 숫자를 입력해주세요!")
            continue
        }
        gameCount += 1
        let (strikeCount, ballCount) = getGameResults(of: cleanedNumbers)
        
        if strikeCount == 3 {
            isGameOn = false
            gameOrder += 1
            print("🎉🎉🎉🎉🎉🎉\n🎉정답입니다!🎉\n🎉🎉🎉🎉🎉🎉")
            gameRecord[gameOrder] = gameCount
        } else {
            print("\(strikeCount)스트라이크 \(ballCount)볼")
        }
    }
    computerNumbers = makeRandomNumberWithZero()
    gameCount = 0
}
  • 게임은 임의로 끝내기 전까지 계속 실행되어야하기 때문에 while문을 활용했다.

✏️ 더 공부해 볼 점!

  • Print문 안의 String들은 enum으로 분리해서 rawValue를 불러오는게 나아 보인다.
  • 메서드 기능을 분리해야 할 거 같다. 너무 여러 기능들을 하고 있다.(정답 판별 기능, 게임을 리셋하는 기능 등)

📌 게임을 플레이한 횟수 보여주기

func showRecord() {
    if gameRecord.count == 0 {
        return
    } else {
        for num in 1...gameOrder {
            print("\(num)번째 게임 : \(gameRecord[num]!) 번 시도")
        }
    }
}
  • 서로 관련있는 값이기에 어떤 회차에 몇 번 시도해서 맞혔는지를 Dict에 담아주고 순회하면서 보여주도록 만들었다.
  • 처음에 게임 기록이 없을 경우를 생각하지 않아서 크래시가 나서 Dict안에 값이 없을 경우도 다룰 수 있도록 수정했다.
profile
iOS 개발

0개의 댓글