Watch Code Kata

Download Code Kata

List of Katas

Kata: Bowling Kata

As described here: http://butunclebob.com/ArticleS.UncleBob.TheBowlingGameKata. Plus handling partial games. Further discussion at http://qualityswdev.com/2011/03/14/the-bowling-game-kata-in-scala/

  • Framework: scala.junit
  • Author: Manuel Küblböck
  • Twitter: ManuelKublbock

Final Solution

// Adapt the code to your code kata primes.
// Important: Test and production code has to be
//            completely in this file.

import org.scalatest.junit.JUnitSuite
import org.scalatest.junit.ShouldMatchersForJUnit
import org.junit.Test

class BowlingGameTest extends JUnitSuite with ShouldMatchersForJUnit {

  val game = new BowlingGame()

  @Test
  def verifyThatAllGuttersScore0() = {
    for (i <- 1 to 20) game roll(0)
    (game score) should be(0)
  }

  @Test
  def verifyThatAllOnesScore20() = {
    for (i <- 1 to 20) game roll(1)
    (game score) should be(20)
  }
  
  @Test
  def verifyThatASpareFollowedByAllOnesScore29() = {
    game roll(5)
    game roll(5)
    for (i <- 1 to 18) game roll(1)
    (game score) should be(29)
  }
  
  @Test
  def verifyThatAStrikeFollowedByAllOnesScore30() = {
    game roll(10)
    for (i <- 1 to 18) game roll(1)
    (game score) should be(30)
  }
  
  @Test
  def verifyThatAPerfectGameScores300() = {
    for (i <- 1 to 12) game roll(10)
      (game score) should be(300)
  }
    
  @Test
  def verifyThatAStartingSpareAnd1Scores12() = {
    game roll(7)
    game roll(3)
    game roll(1)
    (game score) should be(12)
  }


  class BowlingGame {

    var rolls: List[Int] = List()

    def roll(pins: Int) = {
      rolls = rolls :+ pins
    }

    def score: Int = {
      scoreRecursive(0, 1, rolls)
    }

    def scoreRecursive(currentScore: Int, frame: Int, rolls: List[Int]): Int = {
      frame match {
        case 11 => currentScore
        case f => rolls match {
          case 10 :: rollsTail // strike
            => scoreRecursive(currentScore + (rolls take (3) sum), f + 1, rollsTail)
          case first :: second :: rollsTail if (first + second == 10) // spare
            => scoreRecursive(currentScore + (rolls take (3) sum), f + 1, rollsTail)
          case first :: second :: rollsTail // normal
            => scoreRecursive(currentScore + (rolls take (2) sum), f + 1, rollsTail)
          case last :: rollsTail // partial frame
            => currentScore + last
          case nil // partial game
            => currentScore
        }
      }
    }
  }
  
}

Statistics

Framework Started Number of Moves Duration Number of modifications
kata per move kata per move
scala.junit 14-Mar-2011, 08:18:39 PM 27 22m 23s 50 seconds 112 4.1
Chart?chtt=seconds+per+move&cht=bvg&chxt=x,y&chbh=a,0,2&chs=600x200&chxr=1,0,137

Longest three moves

Duration in seconds Move
137 23 Goto move
114 15 Goto move
92 12 Goto move

Sharing

Link to Kata: http://www.codersdojo.org/statistics/38495f8ae5cf0048e3f2897423b64d91198e2648

Short link to Kata: http://bit.ly/idkFqJ

@