Hands-on Scala Programming

Hands-on Scala Programming

Follows my notes on the Haoyi Li.’s book: “Hands-on Scala Programming” (https://www.handsonscala.com/ ).

As an experiment, I coding directly in the org-mode file using Babel to execute the Scala blocks:

TODO Some introduction #

  • Point to dotfiles
  • Point to the Babel package

Notes #

  • Lack of auto-complete when writing here.
  • Compilation errors are hard to track. Workaround is to open a separate buffer with the ammonite REPL console.
  • For sure will have to move to a dedicated project once I use Mill. Or maybe not.

Exercises 3.5 #

3.63 #

“Write a short program that prints each number from 1 to 100 on a new line.

For each multiple of 3, print “Fizz” instead of the number.

For each multiple of 5, print “Buzz” instead of the number.

For numbers which are multiples of both 3 and 5, print “FizzBuzz” instead of the number.”

“Define a def flexibleFizzBuzz method that takes a String => Unit callback function as its argument, and allows the caller to decide what they want to do with the output. The caller can choose to ignore the output, println the output directly, or store the output in a previously-allocated array they already have handy.”

def fizzbuzz(n: Int): String =
    if (n % 3 == 0 && n % 5 == 0) "FizzBuzz"
    else if (n % 3 == 0) "Fizz"
    else if (n % 5 == 0) "Buzz"
    else n.toString()

@main
def main() {
    (1 to 100)
	.map(fizzbuzz)
	.foreach(println)
}

3.64 #

“Write a recursive method printMessages that can receive an array of Msg class instances, each with an optional parent ID, and use it to print out a threaded fashion. That means that child messages are print out indented underneath their parents, and the nesting can be arbitrarily deep.”

  • I assume that the items are ordered by their identifier which is incremental with each new message.
class Msg(val id: Int, val parent: Option[Int], val txt: String)

def printMessages(messages: Array[Msg]) {
  val padding = 2
  def printMessages(index: Int, msgLevel: Map[Int, Int]) {
    if (index < messages.length) {
      val message = messages(index)
      val level = message.parent match {
	case Some(parent) => msgLevel.getOrElse(parent, 0) + 1
	case None => 0
      }

      println(" " * level * padding + message.txt)
      printMessages(index + 1, msgLevel + (message.id -> level))
    }
  }

  printMessages(index = 0, msgLevel = Map())
}

printMessages(Array(
  new Msg(0, None,      "Hello"),
  new Msg(1, Some(0),   "World"),
  new Msg(2, None,      "I am Cow"),
  new Msg(3, Some(2),   "Hear me moo"),
  new Msg(4, Some(2),   "Here I stand"),
  new Msg(5, Some(2),   "I am Cow"),
  new Msg(6, Some(5),   "Here me moo, moo")
))