How to reference instance variable with the same name as a local variable in C++?

Asked

Viewed 251 times

1

In C++, how can I reference an instance variable that has the same name as a global variable? For example, in a set method of the following class:

class Person
{
private:
    string name;

public:
    void setName(string name) 
    {
        //Em java eu faria: this.name = name;
    }

    string getName()
    {
        return name;
    }
};
  • 1

    With this->name https://stackoverflow.com/q/6779645/4438007 ; this is a pointer to the current object

  • 1

    Just like @Jeffersonquesado said, this->name = name;

1 answer

4


In C++, there is a keyword this. It is reserved for contexts where an object is having its method run.

That one this behaves like a constant, constant that is a pointer to the class from which the method is being executed. Of course, it needs to be an instance method, static methods cannot refer to the object itself.

To be exact, this is a prvalue

In fact, every reference to an instance method or attribute within the object is treated as having an implicit call to this->. In his example:

string getName()
{
    return name;
}

If used fully explicitly it would be:

string getName()
{
    return this->name;
}

Among other functions, explicitly call the this is used to disambiguate. For example, in your setter, there is a parameter called name, parameter name that "throws a shadow" over the instance variable name.

In English, it is said that "the Parameter Shadows the Member with the same name"

To resolve this situation, one can use the this so that everything is unambiguous:

void setName(string name) 
{
  this->name = name;
}

(Anti-)C++ nomenclature standards

Because of such problems, some C++ schools preach which instance variables should start with "_". Then it would be used _name for the variable and name for the parameter. In general, your code would look like this (if you were to follow the guidelines of this school):

class Person
{
private:
    string _name;

public:
    void setName(string name) 
    {
        _name = name;
    }

    string getName()
    {
        return _name;
    }
};

I personally find this exit pragmatic but ugly. I wouldn’t use it.

Another use would be in builders; for the case of Person have a constructor that receives as argument a string referring to the name:

Person::Person(string name) {
  _name = name;
}

But this encoding style doesn’t use the more elegant features of C++ to build objects.

Using initializer in constructor

Out of the world where there is "_" before the name of the internal variables, you can very well use initializers in the constructor. For example, in the constructor that receives a string and initializes the attribute name of the object:

Person::Person(string name) : name(name) {
}

In this syntax, the attribute name is initialized with the value in parentheses, which in this context is the parameter name. Generally speaking, this initializer can be understood more or less like this:

<assinatura construtor> : <atributo> ( <valor de inicialização> )

Where:

  • <assinatura construtor> is the signature of the builder (Person::Person(string name))
  • <atributo> is the name of the attribute that will be initialized (the first name, that comes before the parentheses)
  • <valor de inicialização> is the value that will be assigned to the attribute (in this case, the name within parentheses, which corresponds to the constructor parameter)

Some additional search sources:

Browser other questions tagged

You are not signed in. Login or sign up in order to post.