【问题标题】:In current Scala, is there a cleaner way to do the "lazy constructor pattern"在当前的 Scala 中,是否有一种更简洁的方法来执行“惰性构造函数模式”
【发布时间】:2012-02-04 23:37:01
【问题描述】:

最近的东西

case class Foo(lazy next: Foo)

我能想到的是

class Foo(_next: =>Foo) {
    lazy val next = _next
}
object Foo {
    def apply(next: =>Foo) = new Foo(next)
    def unapply(foo: Foo) = Some(foo.next)
}

我发现了一个列出的问题add lazy parameters,所以我想它会被添加 有一天。同时,有没有人知道比上面更干净的技巧?

【问题讨论】:

  • 值得一提的是,您的 unapply 方法并不懒惰,因此尝试将 Foo 模式匹配到另一个 Foo 将导致 next 被评估,您可能不想要.
  • @BrianMcCutchon 这是一个很好的观点。我想让它变得懒惰的唯一方法是添加间接性,如def unapply(foo: Foo) = Some(() => foo.next) ?
  • 这似乎行得通。我只是避免在我的惰性案例类中使用unapply。但是,在这种情况下,您需要显式调用该函数,例如 case Foo(n) => Foo(doSomething(n()))。此时,使用Need 可能会更好。 (另外,如果你走Need 路由,你可以为Foo 定义一个重载的构造函数,它接受一个按名称调用的参数并将其转换为Need。)

标签: scala constructor lazy-evaluation


【解决方案1】:

也许是scalaz.Need?这是在this answer 中向我建议的。

scala> case class Foo(next: Name[Foo])
defined class Foo

scala> lazy val x: Foo = Foo(Need(y)); lazy val y: Foo = Foo(Need(x))
x: Foo = <lazy>
y: Foo = <lazy>

scala> x.next.flatMap(_.next).value eq x
res61: Boolean = true

【讨论】:

  • 我想这是否更干净是有争议的。但混乱在不同的地方,所以无论哪种方式,它都是一个有用的替代方案。
  • @Owen,这就是我过去采用的方法。我也想获得一流的语言支持。
猜你喜欢
  • 1970-01-01
  • 2017-07-09
  • 2019-01-27
  • 2023-04-09
  • 2011-11-05
  • 1970-01-01
  • 2011-12-18
  • 1970-01-01
  • 2010-09-05
相关资源
最近更新 更多