简体   繁体   中英

C++ candidate function not viable?

Why the following code doesn't compile:

B b1(1), b2(2), b3(3);
const B b4 = b1 + (b2 + b3);

Until I replace this:

B operator+(B& b) {
    return B(n + b.n);
}

with this:(I don't know why to write const the compiler suggested that)

B operator+(const B& b) {
    return B(n + b.n);
}

Errors I get:

invalid operands to binary expression ('B' and 'B')

note: candidate function not viable: expects an l-value for 1st argument

note: candidate template ignored: could not match 'reverse_iterator' against 'B' operator+(typename reverse_iterator<_Iter>::difference_type __n, const reverse_iterator<_Iter>& __x)

Plus, why this works? (it's similar to the previous case)

bool Test(int x)
{
    return x==0;
}
Test(0);
 const B b4 = b1 + (b2 + b3);

According to the order of operations, the first subexpression to evaluate is b2 + b3 . This invokes B::operator+ , which returns a B object. More precisely, a temporary B object is returned, one that will be used to help evaluate this full expressions and then discarded. This is much like making notes on scratch paper as you work through a long calculation by hand.

The next subexpression to evaluate is b1 plus the temporary object. This invokes b1.operator+ with the temporary B object as the argument. When the operator's signature is

B operator+(B& b)

there is a problem because the C++ language states that a non- const reference cannot bind to a temporary object . That is, the reference parameter ( B& b ) does not match the temporary object. You can solve this by changing the reference from one that is not const -qualified to one that is.

B operator+(const B& b)

This version of the operator takes a const reference, which can bind to a temporary object. (Again, this is simply a rule of the language. You can debate the reasons for it, but the rule still stands.)

Note that this is not a full solution since addition tends to be symmetric. To accommodate the scenario where the left side of the parentheses is const -qualified, *this also needs to be const -qualified.

B operator+(const B& b) const

For more tips, see the basic rules and idioms for operator overloading . You might find that you don't necessarily want operator+ to be a member function.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM