Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What does a plus sign mean in front of a char array? [duplicate]

I was reading this answer today and noticed a plus sign in front of the char arrays, but don't know what does it mean.

Given the compilation error when I remove it I can guess it is something to help the compiler to infer the return type, but I don't know how it works.

Test code (also here):

#include <iostream>

using namespace std;

auto& operator<<(std::ostream& os, const char (&s)[2]) {
    return os << (*s == ' ' && !s[1] ? +"\n" : +s);
}

int main() {
    cout << "Hello" << " " << "world" << " " << 2018;

    return 0;
}

When removing the plus signs (sample) it doesn't compile:

main.cpp: In function 'auto& operator<<(std::ostream&, const char (&)[2])':

main.cpp:6:48: error: use of 'auto& operator<<(std::ostream&, const char (&)[2])' before deduction of 'auto'

return os << (*s == ' ' && !s[1] ? "\n" : s);
                                            ^

main.cpp: In function 'int main()':

main.cpp:10:24: error: use of 'auto& operator<<(std::ostream&, const char (&)[2])' before deduction of 'auto'

cout << "Hello" << " " << "world" << " " << 2018;
                    ^~~
like image 728
cbuchart Avatar asked Oct 03 '18 07:10

cbuchart


2 Answers

Built-in unary operator+ could take pointer type (but not array type) as its operand, so using it on an array causes array-to-pointer decay, then +"\n" and +s would return const char *.

On the other hand, if you remove the usage of operator+, you'll try to pass the array with type const char[2] to os, which leads to recursive invocation, as the error message tried to tell you.

For the built-in operator, expression must have arithmetic, unscoped enumeration, or pointer type. Integral promotion is performed on the operand if it has integral or unscoped enumeration type and determines the type of the result.

The built-in unary plus operator returns the value of its operand. The only situation where it is not a no-op is when the operand has integral type or unscoped enumeration type, which is changed by integral promotion, e.g, it converts char to int or if the operand is subject to lvalue-to-rvalue, array-to-pointer, or function-to-pointer conversion.

like image 144
songyuanyao Avatar answered Nov 12 '22 10:11

songyuanyao


It's unary plus. The built-in operator can only be applied to numerical types and pointers. All it does is cause an implicit conversion if one is required, and return the operand unchanged.

Since s is a reference to an array, it cannot have + applied before it decays to a pointer, so the operator forces the array-to-pointer conversion to occur.

The reason it must be done is that "\n" is itself a const array of two characters. Since the conditional expression has the common type of its second and third operand, it would have the type char const(&)[2] unless one operand was coerced into a pointer beforehand.

And you can guess which overload of operator<< will be called for char const(&)[2] can you not?

like image 44
StoryTeller - Unslander Monica Avatar answered Nov 12 '22 10:11

StoryTeller - Unslander Monica