перегрузка конструктора класса case с неявным параметром? - PullRequest
1 голос
/ 04 марта 2012

Я пытаюсь определить класс дел с некоторыми параметрами, имеющими значение по умолчанию, но значение по умолчанию требует неявного параметра. Я пробовал что-то вроде этого:

case class ChannelLatches(started: TestLatch, stopped: TestLatch)(implicit system: ActorSystem) {
  def this()(implicit system: ActorSystem) = this(new TestLatch(), new TestLatch())(system)
}

и это:

case class ChannelLatches(started: TestLatch, stopped: TestLatch)(implicit system: ActorSystem) {
   def this()(implicit system: ActorSystem) = this(new TestLatch(), new TestLatch())(system)
}

но в обоих случаях компилятор не распознает мой новый конструктор. Есть указатели?

1 Ответ

4 голосов
/ 04 марта 2012

Проблема не в классе дела или его конструкторе. Когда вы получаете ошибку компиляции, как

scala> val channelLatches = new ChannelLatches
<console>:11: error: could not find implicit value for parameter system: ActorSystem
       val channelLatches = new ChannelLatches
                            ^

это означает, что у вас нет неявной переменной типа ActorSystem, доступной в качестве одного идентификатора в области.

Оба ваших примера кода (это точно один и тот же код, верно?) И пример @ Eastsun - совершенно законный код:

scala> class ActorSystem
defined class ActorSystem

scala> class TestLatch
defined class TestLatch

scala> case class ChannelLatches(started: TestLatch = new TestLatch, stopped: TestLatch = new TestLatch)(implicit system: ActorSystem)
defined class ChannelLatches

scala> implicit val actor = new ActorSystem
actor: ActorSystem = ActorSystem@586f403e

scala> val channelLatches = new ChannelLatches
channelLatches: ChannelLatches = ChannelLatches(TestLatch@521a74af,TestLatch@46e2b745)

Обратите внимание на неявный val-фактор, который позволяет компилятору неявно указывать отсутствующий параметр.

См. Обзор Scala: неявные параметры для ознакомления с неявными параметрами.

--- Edit 2012-03-05: Добавлен альтернативный пример, в котором ChannelLatches является внутренним классом Something

Если вы хотите, чтобы ChannelLatches были внутренним классом чего-либо, вам действительно не нужно передавать экземпляр ActorSystem во внутренние экземпляры класса, поскольку внутренние классы могут получать доступ к значениям из внешних объектов. Путешествие по Скале: Внутренние занятия

scala> class ActorSystem
defined class ActorSystem

scala> class TestLatch
defined class TestLatch

scala> class Something(implicit val as: ActorSystem) {
     |   case class ChannelLatches(started: TestLatch, stopped: TestLatch) {
     |     def this() = this(new TestLatch(), new TestLatch())
     |  
     |     def actorSystem = as
     |   }
     | }
defined class Something

scala> implicit val as = new ActorSystem
as: ActorSystem = ActorSystem@5481be8a

scala> val s = new Something
s: Something = Something@7139acf

scala> val cl = new s.ChannelLatches
cl: s.ChannelLatches = ChannelLatches(TestLatch@38764254,TestLatch@5bfcb5c1)

scala> cl.actorSystem == as
res0: Boolean = true
...