简体   繁体   中英

Self referential View/Context bound

I am actually not clear whether the following were a view or context bound. Also not clear what the self referential aspect (re-referencing Model) is doing ;) :

abstract class Model[M <: Model[M]] extends Transformer {

An explanation on the meaning of "<: Model[M]" would be appreciated.

<: is neither a view nor context bound, but a type bound.

Below is an extended example of how self referential type bounds can be used.

The class ModelA uses a more restrictive type bound M <: ModelA[M] in order to make the method fooN work. ModelA2 can still extend ModelA[ModelA1] , but not ModelA[ModelB1] . On the other hand, the class ModelB doesn't further restrict the type bound, so ModelB2 can extend ModelB[ModelA1] . The methods bar1 and bar2 restrict either the type bound or the parameter model , depending on the order in which the methods transform and bar are called on model .

object Main extends App {
  val a: ModelA1 = foo(new ModelA1(), 2)
  val b: ModelA1 = foo(new ModelA2(), 3)
  val c: ModelB1 = bar1(new ModelB1())
  val d: ModelA1 = bar2(new ModelB2())

  def foo[M <: ModelA[M]](model: Model[M], n: Int): M = model.transform.fooN(n)

  def bar1[M <: ModelB[M]](model: Model[M]): M = model.transform.bar

  def bar2[M <: Model[M]](model: ModelB[M]): M = model.bar.transform
}

abstract class Model[M <: Model[M]] {
  def transform: M
}

abstract class ModelA[M <: ModelA[M]] extends Model[M] {
  def foo: M

  def fooN(n: Int): M = {
    var x: M = this.foo
    for (_ <- 2 to n)
      x = x.foo
    x
  }
}

abstract class ModelB[M <: Model[M]] extends Model[M] {
  def bar: M
}

class ModelA1 extends ModelA[ModelA1] {
  override def transform: ModelA1 = ???
  override def foo: ModelA1 = ???
}

class ModelA2 extends ModelA[ModelA1] {
  override def transform: ModelA1 = ???
  override def foo: ModelA1 = ???
}

class ModelB1 extends ModelB[ModelB1] {
  override def transform: ModelB1 = ???
  override def bar: ModelB1 = ???
}

class ModelB2 extends ModelB[ModelA1] {
  override def transform: ModelA1 = ???
  override def bar: ModelA1 = ???
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM