问题
I want to modify a constructor to use an initialization list as in the following example:
class Foo
{
public:
Foo(std::wstring bar);
private:
std::wstring bar;
};
// VERSION 1:
Foo::Foo(std::wstring bar) {this->bar = bar}
// VERSION 2:
Foo::Foo(std::wstring bar) : this->bar(bar) {} // ERROR!
Unfortunately I can't do version 2 because you can't use the this
pointer for data members since (I'm guessing) they don't exist yet at that point. How then, do I deal with the name hiding issue (i.e. my parameter and my data member have the same name)?
回答1:
You don't need to. The first bar
will refer to the member and the second bar
will refer to the argument:
Foo::Foo(std::wstring bar) : bar(bar) {}
回答2:
I would change the name of the argument so it's clear which is which.
Foo::Foo(std::wstring b) : bar(b) {}
Note that you don't strictly have to, but future maintainers of your code will probably thank you.
Alternate option:
It's common in C++ to denote private member variables with a special naming convention, for example a trailing underscore. That solves this problem nicely:
class Foo
{
public:
Foo(std::wstring bar);
private:
std::wstring bar_;
};
Foo::Foo(std::wstring bar) : bar_(bar) {}
回答3:
You can actually do this:
Foo::Foo(std::wstring bar) : bar(bar) {}
Everything initializer used after the :
must refer to either a base class or some member. That means your bar
member won't be hidden at that point.
回答4:
The compiler will know what to do... just remove this->
来源:https://stackoverflow.com/questions/14716337/name-hiding-in-constructor-initialization-list