0
votes

Is it possible to override a 'val' type on a Scala constructor?

Given a class such as this:

class GPPerson (id: Option[GPID], created: Option[DateTime], active: Boolean, primaryEmail: String)

I'd like to create a constructor that can essentially do this:

if (created == None) created = new DateTime

In other words, if a None value is supplies, replace it with a DateTime instance. The catch is, I'm trying to avoid using a companion object, and the 'created' object needs to be 'val' (can't make it a 'var').

2
Why are you avoiding using a companion object? That's kinda just... how you do it.Chris Martin
The companion object will complicate things. It's not impossible, but like I said "trying to avoid." These are TableQuery classes in Slick, and introducing a companion object causes implicit conversation to break... (eg., tupled() method is 'lost' because of apply() methods). That can be fixed by implementing an explicit tupled() BUT... this is basically a template for all of our models so I'm trying to keep it as simple as possible.Zac

2 Answers

2
votes

Constructor parameters may have a default value:

class GPPerson (id: Option[GPID], created: Option[DateTime] = Some(new DateTime), active: Boolean, primaryEmail: String)
// to instantiate it:
new GPPerson(id = Some(id), active = false, primaryEmail = myEmail)

You might want to reorder the parameters so optional parameters are the last ones, then you can omit the parameter name:

class GPPerson (id: Option[GPID], active: Boolean, primaryEmail: String, created: Option[DateTime] = Some(new DateTime))
// to instantiate it:
new GPPerson(Some(id), false, myEmail)
1
votes

One approach is

class GPPerson (id: Option[GPID], _created: Option[DateTime], active: Boolean, primaryEmail: String) {
  val created = _created.getOrElse(new DateTime)
}

Another:

class GPPerson (id: Option[GPID], created: DateTime, active: Boolean, primaryEmail: String) {
  def this(id: Option[GPID], _created: Option[DateTime], active: Boolean, primaryEmail: String) = this(id, _created.getOrElse(new DateTime), active, primaryEmail)
}

though for this specific case I'd go with @JhonnyEverson's solution.