tags:

views:

120

answers:

2

This code

class Foo(str: String) {
    val len = str.length
    def getLen = len
    def getStr = str}

will be compiled to

public class Foo implements ScalaObject
{

    private final int len;
    private final String str;
    public Foo(String str)
    {
        this.str = str;
        super();
        len = str.length();
    }

    public String getStr()
    {
        return str;
    }

    public int getLen()
    {
        return len();
    }

    public int len()
    {
        return len;
    }

    public int $tag()
        throws RemoteException
    {
        return scala.ScalaObject.class.$tag(this);
    }
}

But this code

class Foo(str: String) {
    val len = str.length
    def getLen = len
}

will be compiled to

public class Foo implements ScalaObject
{

    private final int len;

    public Foo(String str)
    {
        len = str.length();
    }

    public int getLen()
    {
        return len();
    }

    public int len()
    {
        return len;
    }

    public int $tag()
        throws RemoteException
    {
        return scala.ScalaObject.class.$tag(this);
    }
}

Why there is no private member in class Foo?

private final String str;

Is it some sort of optimization?

Why it is allowed to point to constructor's parameters. Why there is no compile-time error for line "def getStr = str"?

+1  A: 

Well, according to Odersky book, the constructor is the only place where you can match fields to the constructor arguments. If you don't do it there will be no variable seen outside the constructor.

Ashalynd
+2  A: 

In Scala, constructor parameters are visible from anywhere within the class, I see it more like "object parameters". In your second snippet it wasn't compiled to create a class attribute for it simply because you're not referencing it outside the constructor - it is not needed.

Germán
But who should manage the lifetime of objects which was used as constructor parameters?
Vladimir Bezugliy
I'm not sure I understand the question... as usual objects might be GC'd when no references exist. Your Foo class doesn't manage that object's lifetime (it was instantiated somewhere else, and who knows how many references are around). The compiles simply makes sure not to keep a reference when this is not needed. This may or may not make it a GC candidate sooner, depends on what's being done with it elsewhere.
Germán