Reputation: 298908
I have a Binary Search Tree implementation that uses an Ordering
:
case class Bst[T](rootNode: Node[T]) {
def this(rootValue: T, o: Ordering[T]) = this(Node(rootValue, o))
def +=(value: T) = {
val node: Node[T] = rootNode.withValue(value)
node match {
case it if it == rootNode => this
case _ => new Bst[T](node)
}
}
}
case class Node[T](value: T,
ordering: Ordering[T],
left: Option[Node[T]] = None,
right: Option[Node[T]] = None) {
def withValue(v: T): Node[T] = {
ordering.compare(v, value) match {
case comp if comp < 0 =>
Node(value, ordering, node(left, v), right)
case comp if comp > 0 =>
Node(value, ordering, left, node(right, v))
case _ => this
}
}
private def node(ref: Option[Node[T]], v: T): Option[Node[T]] = {
ref.map(_.withValue(v)) orElse Some(Node(v, ordering))
}
}
It works fine if I call it using new and with an explicit Ordering
:
object Tester {
def main(args: Array[String]) {
val bst = new Bst[Int](12, Ordering.Int) += 4 += 115 += 19 += 333
}
}
But I'd like to initialize it without new
and preferably also without the explicit Ordering
. But I'd like the class to still support different generic types. What do I need to do?
Upvotes: 0
Views: 270
Reputation: 18859
You can define an explicit companion object for Bst
:
object Bst {
def apply[T](rootValue: T, o: Ordering[T]) = new Bst(rootValue, o)
}
And then you can use Bst(1, Ordering.Int)
to create a Bst
instance.
scala> Bst(12, Ordering.Int) += 4 += 115
res0: Bst[Int] = Bst(Node(12,scala.math.Ordering$Int$@42c2b246,Some(Node(4,scala.math.Ordering$Int$@42c2b246,None,None)),Some(Node(115,scala.math.Ordering$Int$@42c2b246,None,None))))
If you want to create object without explicit Ordering
, you can define as:
object Bst {
def apply[T: Ordering](rootValue: T) = new Bst(rootValue, implicitly[Ordering[T]])
}
Then:
scala> Bst(1)
res1: Bst[Int] = Bst(Node(1,scala.math.Ordering$Int$@42c2b246,None,None))
Upvotes: 4