0

The following code runs for both var = putVar; & this.var = putVar;

I understand: "this" is used to identify that - "put this value for just 'my' object". When both work, why do people usually use "this" in setters?

code:

public class PlayingWithObjects
{
    public static void main(String[] args)
    {
        SomeClass classObj = new SomeClass(10);

        System.out.println("classObj.getVar: " + classObj.getVar() );

        classObj.setVar(20);

        System.out.println("classObj.getVar: " + classObj.getVar() );

        classObj = new SomeClass(30);

        System.out.println("classObj.getVar: " + classObj.getVar() );
    }
}

class SomeClass
{
    private int var;

    public SomeClass(int putVar)
    {
        var = putVar;
    }

    public int getVar()
    {
        return var;
    }

    public void setVar(int putVar)
    {
//      var = putVar;           // also works
        this.var = putVar;
    }
}

Am I understanding "this" correctly? Where is "this" used & cannot be replaced. Please post some code.

MdT
  • 871
  • 3
  • 10
  • 15
  • 2
    Usually just to make it very clear that they're referring to the member of the current object. – Tushar Mar 30 '13 at 05:17
  • @Tushar: so this is just good practice to use this.var in constructors & setters? does "this" have any other uses? – MdT Mar 30 '13 at 05:19
  • 1
    In your case, where the local variable and object member have different identifiers, that's the main one. If you're in an anonymous inner class within another object (ex: of class `ClassName`), you can use `ClassName.this` to get the instance of the enclosing object. The reason for this (no pun intended) is that, inside the inner class, `this` will refer to the inner class. – Tushar Mar 30 '13 at 05:21
  • May be this [question](http://stackoverflow.com/questions/2429062/java-when-to-use-this-keyword) will help – Rahul Gautam Mar 30 '13 at 05:25
  • 'Why do people usually use 'this' in setters?' They do? Evidence? *I* do, but I always use the same name in the parameters, so I have to. I don't know what people 'usually' do. – user207421 Mar 31 '13 at 03:10

5 Answers5

7

Because people like to use the same variable name for both the method parameter and the instance variable - in which case you need this to differentiate.

public void setX(int x) {
    this.x = x;
}
ktm5124
  • 11,861
  • 21
  • 74
  • 119
2

You can use this if you're using the same method argument identifier as a field, but it can be avoided if you simply do not use the same name.

Not using the same name is a more common practice to avoid confusion and shadowing. Hence, any reference to this in a setter can be replaced with a better naming standard: inParameter, for instance.

public void setX(int inX) {
    x = inX;
}

The other use of this would be to explicitly invoke a constructor. This is a form which can't be replaced with a simpler naming convention:

public class Foo {

    private String name;

    public Foo() {
        this("");
    }

    public Foo(String inName) {
        name = inName;
    }
}

There may also be a case in which you want to return the instance you're working with. This is also something that this allows you to do:

return this;
Makoto
  • 104,088
  • 27
  • 192
  • 230
  • Right, invoking a constructor was the one I was missing. – Tushar Mar 30 '13 at 05:28
  • This is where I need some help. Can you give a simple example where I would return this; – MdT Mar 30 '13 at 05:38
  • 1
    A good example of returning `this` is when you want to implement method chaining (Google App Engine does this with query building, IIRC). – ktm5124 Mar 30 '13 at 05:43
1

There are 2 cases I know of, aside from the case ktm mentioned (which I think is obvious and you already knew):

  1. Just to make it very clear that they're referring to the member of the current object.

    void foo(int x) {
        this.y = x; // No mistaking that y belongs to the object
    }
    
  2. If you're in an anonymous inner class within another object (ex: of class ClassName), you can use ClassName.this to get the instance of the enclosing object. The reason for this (no pun intended) is that, inside the inner class, this will refer to the inner class.

    SomeInnerClass myObj = new SomeInnerClass() {
        void bar() {
            this.y = 0; // this refers to the SomeInnerClass object
            OuterClass.this.y = 0; // OuterClass.this refers to the enclosing class OuterClass object
        }
    };
    
Tushar
  • 8,019
  • 31
  • 38
0

Like ktm mentioned, setters tend to use the same name as the field for the parameter. In this case, the parameter shadows the field name, so

public void setX(int x) {
    x = x;
}

would just set the parameter to itself rather than setting the field to the parameter.

osandov
  • 121
  • 1
  • 4
0

If a class has an instance variable with some name (say myVar), and a method has a LOCAL variable with the exact same name (myVar), then any reference to the variable will refer to the LOCAL variable. In cases such as these, if we want to specify the class's instance variable, we need to say this.myVar. As stated before, this is particularly useful when we want to have setters in which the parameter name is the same as the instance variable that it sets:

public void setMyVar(int myVar) {
    this.myVar = myVar; // If we said myVar = myVar;, we'd just set the local
                        // variable to itself, which would NOT be what we want.
}
Jimmy Lee
  • 1,001
  • 5
  • 12