Tango Xiao
Tango Xiao

Reputation: 329

Why does the statement “vector<int>(v1);” fail

A vector<int>(v1) expression yields a temporary object, and can be put on the right side of operator=, but if we use a vector<int>(v1) expression as a statement, it will fail in Visual Studio 2010 10.0.30319.1 RTMRel. Detailed error information is in comments in the following code. Why does this happen?

vector<int> v1; 
v1.push_back( 10 );
v1.push_back( 20 );
v1.push_back( 30 );    
vector<int> v3 = vector<int>(v1);  //OK, deliberately code like this.
vector<int>(v1);  //error C2086: “std::vector<_Ty> v1”: redefinition

In the book “C++ Coding Standards: 101 Rules, Guidelines, and Best Practices”, chapter 82 "Use the accepted idioms to really shrink capacity and really erase elements". There is a statement:

container<_Type>(c).swap(c);

I don’t understand and just want to test container<_Type>(c), what does it mean?

Upvotes: 6

Views: 366

Answers (3)

zdf
zdf

Reputation: 4808

I understand that vector<int>(v1) is counterintuitive, but I do not see the point of using it. As others pointed out, this is standard behavior. If you're looking for a solution, here are 2 workarounds:

vector<int>::vector( v1 );
vector<int> { v1 };

EDIT (the question has changed): "container<_Type>(c).swap(c); I don’t understand..." This is different from container<_Type>(c);. A container may have a capacity larger than the one reported thru size (see reserve). The reserve helps minimize the number of some operations. If you add a new element, the container uses the already allocated memory. For instance, your vector might have room for 10 elements but it actually has only 1. If you add a new element, room for 8 elements is left. The above construct removes the reserve in order to conserve memory. First a copy of the original is made (this copy has no reserve). Then, the underlying data (pointer) of the original vector is replaced (see swap) by the new one, and the temporary object (which now owns the memory of the original) is discarded .

"...to test container<_Type>(c), what does it mean?" Used as above it means "create a temporary copy of c". Used in isolation, it looks like a copy constructor, but in fact it declares an object. The difference is given by the dot operator.

Upvotes: 1

πάντα ῥεῖ
πάντα ῥεῖ

Reputation: 1

vector<int>(v1) expression yields a temporary object, and can be put on the right side of operator=, but if we use vector<int>(v1) expression as a statement, We will fail ...

The plain statement is handled differently by the compiler:

vector<int>(v1); //error C2086: “std::vector<_Ty> v1”: redefinition

Is an alternative way of writing

vector<int> v1;

So you're redefining v1 and the compiler complains.


To see your temporary initialization working use for instance

void foo(const std::vector<int>& v)
{
}

and call

foo(vector<int>(v1));

or simply1

(std::vector<int>)(v1); // this creates a temporary which is immediately disposed

See live demo for the latter


1)Stolen from @Sergey A's answer, but he preferred to delete it

Upvotes: 4

αλεχολυτ
αλεχολυτ

Reputation: 5050

vector<int>(v1); is same as vector<int> v1;. i.e. variable redefinition.

Upvotes: 6

Related Questions