1

在 Scalaz 中object Need我发现

def apply[A](a: => A) = {
  lazy val value0: A = a
  new Need[A] {
    def value = value0
  }
}

这和(对我来说更自然)有什么区别

def apply[A](a: => A) = {
  new Need[A] {
    private lazy val value0: A = a
    def value = value0
  }
}

在性能、生成的代码等方面?

4

1 回答 1

2

在时间或空间要求严格的应用程序中,您通常应该更喜欢第二个。原因隐藏在字节码中。具体来说,如果我们有

abstract class Foo { def value: Int }
class Bar {
  def out(i: => Int) = {
    lazy val v0 = i
    new Foo { def value = v0 }
  }
  def in(i: => Int) = new Foo {
    private lazy val v0 = i
    def value = v0
  }
}

然后在第二种情况下,我们向字节码添加一个私有的v0: Intbitmap$0: Boolean,加上标准的惰性 val 访问器。然而,在第一种情况下,我们改为添加 av0$lzy$1: runtime.IntRef和 abitmap$0$1: runtime.VolatileByteRef来引用等价物IntBooleanout方法体中创建。因此,我们有一个额外的包装层。

在我的机器上,创建对象和检索一次out的版本比版本长约 50% 。invalue

于 2013-07-14T18:53:12.463 回答