scala特征(或抽象类):在实例化实例化时设置时间戳变量(或参数)

时间:2017-10-27 18:42:06

标签: scala

我有一个特征和几个案例类继承自它。像这样:

sealed trait Event
case class Meeting(name: String)
case class Call(number: String)

我想为每个事件实例添加一个时间戳。我们的想法是在实例化期间为每个类实例设置时间戳。将它放在每个case类定义中都很容易。但我想知道我是否可以某种方式将其放入Event

2 个答案:

答案 0 :(得分:2)

鉴于案例类语义(.equals.hashCode.toString等),您可能更喜欢这样:

import java.time.LocalDateTime

sealed trait Event {
  val time: LocalDateTime
}

final case class Meeting(name: String, override val time: LocalDateTime = LocalDateTime.now())
extends Event

final case class Call(number: String, override val time: LocalDateTime = LocalDateTime.now())
extends Event

不可否认,这不是那么优雅,但它会更加一致。例如,请考虑此 Scala REPL 会话:

scala> val m1 = Meeting("Some meeting")
m1: Meeting = Meeting(Some meeting,2017-10-27T17:15:37.389)

scala> val m2 = Meeting("Some meeting")
m2: Meeting = Meeting(Some meeting,2017-10-27T17:15:46.829)

scala> m1 == m2
res0: Boolean = false

m1m2不相等,因为它们的开始时间不同。

您还可以使用案例类的全部功能,时间模式匹配等,同时将MeetingCall视为Event。例如:

val events: List[Event] = //...

// Filter events that occurred in the last week.
val oneWeekAgo = LocalDateTime.now().minusDays(7)
val recent = events.filter(_.time.isAfter(oneWeekAgo))

// Convert to log messages.
val msg = recent.map {
  case Meeting(n, t) => s"Meeting $n, held on ${t.toString}"
  case Call(n, t) => s"Telephone call to $n, made on ${t.toString}"
}

此版本也更容易测试,因为可以包含明确的开始时间。

答案 1 :(得分:0)

您可以在特质中声明它

  sealed trait Event {
    val time = LocalDateTime.now()
  }
  case class Meeting(name: String) extends Event
  case class Call(number: String) extends Event