Skip to content

Instantly share code, notes, and snippets.

@vascorsd
Created August 19, 2016 16:48
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 vascorsd/e5ae34e5309e95112f426cba54cdd02b to your computer and use it in GitHub Desktop.
Save vascorsd/e5ae34e5309e95112f426cba54cdd02b to your computer and use it in GitHub Desktop.
Some tests around checking relationship of some Nodes. Includes Typeclass :D
case class Node(id: Long, parent: Option[Long])
trait TreeNode[T] {
def id(n: T): Long
def parentId(n: T): Option[Long]
}
object TreeNode {
def apply[A](implicit A: TreeNode[A]): TreeNode[A] = A
implicit val nodeX: TreeNode[Node] = new TreeNode[Node] {
override def id(n: Node): Long = n.id
override def parentId(n: Node): Option[Long] = n.parent
}
}
val n1 = Node(1, None)
val n2 = Node(2, Some(1))
val n3 = Node(3, Some(2))
val nX = Node(4, Some(8))
val nH = Node(5, None)
checkParentship(n2 :: n1 :: Nil) // should work
checkParentship(n3 :: n2 :: Nil) // should work
checkParentship(n1 :: Nil)
checkParentship(n1 :: n2 :: Nil)
checkParentship(n1 :: n2 :: n3 :: Nil)
checkParentship(n1 :: n1 :: Nil)
checkParentship(n3 :: n1 :: Nil)
checkParentship(nH :: n2 :: Nil)
checkParentship(n3 :: nH :: n2 :: Nil)
/**
* Checks that a list of tree nodes form a strict
* path from Leaf > Leaf Parent > Leaf GrandParent > ...
*
* @param xs Requires the list to have at least 2 elements.
* If less a relationship makes no sense.
* @tparam A Accepts a list of As that can be seen as TreeNodes.
* @return false if list has less than two elements.
*
*/
def checkParentship[A: TreeNode](xs: List[A]) = xs match {
case _ :: _ :: _ =>
val ids = xs.map(x => Option(TreeNode[A].id(x))).tail
val parents = xs.map(x => TreeNode[A].parentId(x)).init
ids == parents
case _ => false
}
val ys = Option(n3) :: Option(n2) :: Option(n1) :: Nil
val holes = Option(n3) :: None :: Option(n1) :: Nil
val emptyStartAndHoles = None :: None :: Option(n3) :: None :: Option(n1) :: Nil
val z = ys dropWhile(_.isEmpty)
val zz = holes dropWhile(_.isEmpty)
val zzz = emptyStartAndHoles dropWhile(_.isEmpty)
val v = z.forall(_.nonEmpty)
val vv = zz.forall(_.nonEmpty)
val vvv = zzz.forall(_.nonEmpty)
val properPath = z.flatten
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment