Skip to content

Instantly share code, notes, and snippets.

@ariwaranosai
Created January 5, 2017 14:10
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ariwaranosai/5db2162ae3f60bac4adff221be2720a1 to your computer and use it in GitHub Desktop.
Save ariwaranosai/5db2162ae3f60bac4adff221be2720a1 to your computer and use it in GitHub Desktop.
/**
* Created by ariwaranosai on 2017/1/3.
*
*/
trait ExpAlg[T] {
def lit(n: Int): T
def add(x: T, y: T): T
}
object ExpAlg {
implicit def toIntExpOps[T](n: Int)(implicit m: ExpAlg[T]): ToIntExpOps[T] =
new ToIntExpOps[T](n)(m)
class ToIntExpOps[T](n: Int)(implicit m: ExpAlg[T]) {
def lit[T](implicit m: ExpAlg[T]): T = m.lit(n)
}
implicit def toExpAlgTOps[T](n: T)(implicit m: ExpAlg[T]) =
new ToExpAlgTOps[T](n)(m)
class ToExpAlgTOps[T](n: T)(implicit m: ExpAlg[T]) {
def add(y: T): T = m.add(n, y)
def ++ = add _
}
}
trait MulAlg[T] {
def mul(x: T, y: T): T
}
object MulAlg {
implicit def toMulAlgOps[T](n: T)(implicit m: MulAlg[T]) =
new ToMulAlgOps[T](n)(m)
class ToMulAlgOps[T](n: T)(m: MulAlg[T]) {
def mul(y: T): T = m.mul(n, y)
def ** = mul _
}
}
trait Eval {
def eval: Int
}
import ExpAlg._
import MulAlg._
object EvalInstance {
implicit val evalInstance = new ExpAlg[Eval] {
override def lit(n: Int) = new Eval {
override def eval = n
}
override def add(x: Eval, y: Eval) = new Eval {
override def eval = x.eval + y.eval
}
}
implicit val mulInstance = new MulAlg[Eval] {
override def mul(x: Eval, y: Eval): Eval = new Eval {
override def eval = x.eval * y.eval
}
}
}
object FTT {
def main(args: Array[String]): Unit = {
def e1[T](implicit m: ExpAlg[T]) = {
(1.lit[T] ++ 2.lit[T]) ++ 2.lit[T]
}
def e2[T](implicit m: ExpAlg[T], m1: MulAlg[T]) = {
(1.lit[T] ++ 2.lit[T]) ** 3.lit[T]
}
import EvalInstance._
println(e1[Eval].eval)
println(e2[Eval].eval)
}
}
trait View {
def view: String
}
object ViewExp {
implicit val viewInstance = new ExpAlg[View] {
override def lit(n: Int): View = new View {
override def view = n.toString
}
override def add(x: View, y: View): View = new View {
override def view = s"(${x.view} + ${y.view})"
}
}
implicit val mulInstance = new MulAlg[View] {
override def mul(x: View, y: View): View = new View {
override def view = s"(${x.view} * ${y.view})"
}
}
}
object FTT1 {
def main(args: Array[String]): Unit = {
def e1[T](implicit m: ExpAlg[T]) = {
(1.lit[T] ++ 2.lit[T]) ++ 2.lit[T]
}
def e2[T](implicit m: ExpAlg[T], m1: MulAlg[T]) = {
(1.lit[T] ++ 2.lit[T]) ** 3.lit[T]
}
import ViewExp._
println(e1[View].view)
println(e2[View].view)
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment