Błażej
Błażej

Reputation: 193

What is the difference between stringstream object() and object?

In my program I have

stringstream strumien(); //1
stringstream strumien;  // 2
strumien<<"napis "<<8<<endl;

and the first line generates the following error

invalid operands of types 'std::stringstream() {aka std::basic_stringstream()}' and 'const char [7]' to binary 'operator<<'

But the second one works properly. (of course always one of them is commented out)
So what is the difference between them? Because I always thought that they are equal definitions of an object.

Upvotes: 3

Views: 345

Answers (3)

Pierre Fourgeaud
Pierre Fourgeaud

Reputation: 14530

The first line is in fact a declaration. Even if it seems to be the same as your second, it is not...

So

T name();

declares a function name return an object of type T.

The C++ standard states this ambiguity :

6.8 Ambiguity resolution [stmt.ambig]

There is an ambiguity in the grammar involving expression-statements and declarations: An expression-statement with a function-style explicit type conversion as its leftmost subexpression can be indistinguishable from a declaration where the first declarator starts with a (. In those cases the statement is a declaration.

This ambiguity is also called The Most Vexing Parse.


There is a new way to solve this since the C++11, it is called the uniform initialization syntax.

It works like :

T name{};

Upvotes: 1

Platinum Azure
Platinum Azure

Reputation: 46233

The first line is ambiguous in the formal grammar: Either it could be interpreted as a function declaration or a declaration and instantiation of an object with a no-arg constructor. The language opts to treat it as a function declaration since it is possible to forego the parentheses to invoke the no-arg constructor.

Upvotes: 0

Dietmar K&#252;hl
Dietmar K&#252;hl

Reputation: 154045

Something which looks like a function declaration is a function declaration. That is

T name();

declares a function called name taking no arguments and returning a T. This is called the Most Vexing Parse. There are two potential fixes to avoiding this problem: leaving the parenthesis off or using C++2011 "uniform initialization" (which is a gross misnomer):

T name{};

Upvotes: 8

Related Questions