# Measuring timing in a free algebra

April 06, 2017

Let's build on the `ConsoleIO` example from Free `Coyoneda` in scalaz 7.2 by adding a command to get the current time. We can use this command to measure the evaluation of portions of a program.

``````import java.util.Date
import scalaz.Free
import scalaz.Free.liftF
import scalaz.effect.IO
import scalaz.~>

sealed trait ConsoleOp[A]
type ConsoleIO[A] = Free[ConsoleOp, A]

case class Writeln(x: String) extends ConsoleOp[Unit]
def writeln(x: String): ConsoleIO[Unit] = liftF(Writeln(x))

case class Person(name: String)

val getPerson: ConsoleIO[Person] =
for {
_     <- writeln("What is your name?")
} yield Person(name)

def greetPerson(person: Person): ConsoleIO[Unit] =
writeln(s"Hello, \${person.name}!")``````

Let's add a new command, `GetTime`, that we can use to get the current time during evaluation:

``````case object GetTime extends ConsoleOp[Date]
val getTime: ConsoleIO[Date] = liftF(GetTime)

val program: ConsoleIO[Unit] =
for {
s <- getTime
p <- getPerson
e <- getTime
_ <- writeln(s"That took \${e.getTime - s.getTime} ms.")
_ <- greetPerson(p)
} yield ()

val consoleRunner: ConsoleOp ~> IO =
new (ConsoleOp ~> IO) {
def apply[A](fa: ConsoleOp[A]): IO[A] =
fa match {
case Writeln(x) => IO(println(x))
case GetTime    => IO(new Date())
}
}

program.foldMap(consoleRunner).unsafePerformIO``````

This code can be run with sbt and codedown:

``````/***
libraryDependencies += "org.scalaz" %% "scalaz-core" % "7.2.10"
libraryDependencies += "org.scalaz" %% "scalaz-effect" % "7.2.10"
*/``````
``````\$ curl -s https://earldouglas.com/posts/freetime.md | codedown scala > freetime.scala
\$ sbt -Dsbt.main.class=sbt.ScriptMain freetime.scala