2012-07-23 56 views
5

我在Scala写了一个矩阵类,我认为实现一个转置操作的最好方法就是返回一个接口,并将所有操作“转置”。因此,如果matrix.apply(i, j)返回第(i,j)个元素,则matrix.transpose返回包含返回矩阵(j,i)的apply方法的接口(但不是数据的副本)。而我写的界面有点像这样(我真的写了很多混乱):在Scala中,当内部对象扩展封闭类时会发生什么?

abstract class Matrix { 
    def apply(i : Int, j : Int) : Double 
    //other matrixy operations 
    private def outer = this //so the inner can see the enclosing instance 
    object TransposedInterface extends Matrix { 
     def apply(i :Int, j : Int) = outer(j, i) 
    } 
} 

这是可爱的,我想,但现在TransposedInterface也有一个物体里面叫TransposedInterface,依此类推,递归,这一切都结束了?

我试图解释如下:

class Outer(val i : Int) { 
    object Inner extends Outer(i + 1) 
} 

val o = new Outer(1) 
o.Inner.Inner.Inner.Inner.i 

其中运行和评估为5,像它应该,我猜。

那么究竟发生了什么?内部对象是懒惰评估的吗?当它不是立即被使用时,是否收集垃圾,然后再次实例化outer.Inner被调用?我有没有想过这是一些巫术?

回答

3

它被懒惰地实例化并且不会被垃圾收集,直到外部类被收集,因为外部类包含对它的引用。

一般而言,object Foo { ... }的行为非常像lazy val Foo = { ... }。由于对象在有效时不能为空,但肯定是对象,因此它们在此上下文中更有效(更快地检查存在 - 仅查看该字段是否为空),但缺点是需要第二个.class文件。 (你一般不关心有多少类文件,所以这可能不是什么大问题。)

+0

谢谢!事实证明,知道答案可以更容易地找到[答案](http://stackoverflow.com/questions/3448691/val-and-object-inside-a-scala-class)。 – 2012-07-23 20:59:43

相关问题