简体   繁体   中英

How can I assign a val with the implementation of a trait?

I have the following trait and classes:

trait A{
  def func1: String
  def func2: Int
}
class F extends A{
  def func1: String = ???
  def func2: Int = ???
}
class G extends A{
  def func1: String = ???
  def func2: Int = ???
}

And I want to create the following trait and class:

trait X{
  val a: ***
}
class Z extends X{
  override val a = new G
}

What do I need to write on '***' in trait X so that I can assign val a with a class F or G? Thank you.

EDIT

Sorry, I forgot to mention that trait A is A[Any] and traits F and G can be 'F extends A[String]' and 'G extends A[Int]'. In other words, the classes can extends the trait A with different types of parameters.

Re. your edit, your code fails because trait A only takes type parameter of a fixed type. If you declare base class having a A[Any] , you cannot override it with a A[Int] or A[String] . There are two ways to make your code works.

One is to make trait A type argument covariant , so that you can override with subclass of the type argument you declared in base class (note the + in trait A definition):

  trait A[+T]
  class F extends A[String]
  class G extends A[Int]
  
  trait X {
    val a: A[Any]
  }
  
  class Z extends X {
    val a = new G
  }

See here: Sample

Another way to work is to declare a as a A[_] ( _ means it takes any type as a parameter, which is different from Any ):

  trait A[T]
  class F extends A[String]
  class G extends A[Int]
  
  trait X {
    val a: A[_]
  }
  
  class Z extends X {
    val a = new G
  }

See here: Sample

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