Skip to content

Instantly share code, notes, and snippets.

@nafg
Last active May 12, 2017 01:06
Show Gist options
  • Save nafg/651af0b73705a5f82560dc5bc1f5556d to your computer and use it in GitHub Desktop.
Save nafg/651af0b73705a5f82560dc5bc1f5556d to your computer and use it in GitHub Desktop.
package twentyquestions
import scala.io.StdIn
sealed trait Step
case class Question(text: String, yes: Step, no: Step) extends Step
case class Guess(text: String) extends Step
case class AskYesNo(prompt: String, ifYes: () => Unit, ifNo: () => Unit)
object AskYesNo {
def run(program: AskYesNo) =
StdIn.readLine(program.prompt).toLowerCase match {
case "yes" => program.ifYes()
case "no" => program.ifNo()
}
}
object Main {
def runStep(step: Step): Step = step match {
case q@Question(questionText, yes, no) =>
StdIn.readLine(questionText + " ").toLowerCase match {
case "yes" =>
val newYesBranch = runStep(yes)
q.copy(yes = newYesBranch)
case "no" =>
val newNoBranch = runStep(no)
q.copy(no = newNoBranch)
}
case Guess(guessText) =>
StdIn.readLine("Is it " + guessText + "? ").toLowerCase match {
case "yes" =>
println("I won!")
step
case "no" =>
val answer = StdIn.readLine("I give up. What were you thinking of? ")
val newQuestionText =
StdIn.readLine(
"Enter a question that the answer is 'yes' for " + answer + " and 'no' for " + guessText + ". "
)
Question(text = newQuestionText, yes = Guess(answer), no = Guess(guessText))
}
}
def main(args: Array[String]): Unit = {
val initialModel =
Question(
text = "Is it an animal?",
yes = Guess("an elephant"),
no = Guess("a frying pan")
)
def loop(model: Step): Unit = {
val result = runStep(model)
StdIn.readLine("Do you want to play again? ").toLowerCase match {
case "no" =>
case "yes" => loop(result)
}
}
loop(initialModel)
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment