Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C++ > vector.reserve

Reply
Thread Tools

vector.reserve

 
 
john smith
Guest
Posts: n/a
 
      07-25-2003
HI, when I try the following code, I get a segfault when compiled with
VC.NET and g++ under cygwin.

#1 vector<int> vi;
#2 vector<int>::iterator ii = vi.begin();
#3 vi.reserve(10);
#4 for(int i = 0; i < 10; ++i) {
#5 *ii++ = 4;
#6 }
#7 copy(vi.begin(), vi.end(), ostream_iterator<int>(cout, " "));

Here is my break down on why this code should work (fill a vector with
numbers, nevermind v[i] syntax, or v.push_back(), or the fill(...) stl
function. I really wanted to know why the use of iterators causes a problem
here).

#1 - v.size is 0;
#2 - initiate a interator and point to v.begin().
#3 - make space for 10 more elements, v.size() is still 0;
#4-6 - loop and assign each space in the vector a number. #5 is where segv
happens.

I was under the assumption that reserve will make space available to add
more element, which the iterator will be able to walk through them. I'd
appreciate any help on this issue.

Smith





 
Reply With Quote
 
 
 
 
Daniel Seitz
Guest
Posts: n/a
 
      07-25-2003
Your iterator is invalid. Obtain it after you call reserve();


 
Reply With Quote
 
 
 
 
Daniel Seitz
Guest
Posts: n/a
 
      07-25-2003

Daniel Seitz wrote in message ...
>Your iterator is invalid. Obtain it after you call reserve();
>
>


Oh, and it's not really "invalid", but vi.begin() == vi.end(). I hope no
confusion came of this. Read 23.1, item 7.


 
Reply With Quote
 
yangyong
Guest
Posts: n/a
 
      07-25-2003
vector::reserve increment vector capacity,not size.
capacity and size are diff.

MSDN sample.


#include <iostream>
#include <vector>

using namespace std ;

typedef vector<int> INTVECTOR;

void main()
{
// Dynamically allocated vector begins with 0 elements.
INTVECTOR theVector;

// Add one element to the end of the vector, an int with the value 42.
theVector.push_back(42) ;

// Show statistics about vector.
cout << "theVector's size is: " << theVector.size() << endl;
cout << "theVector's maximum size is: " << theVector.max_size()
<< endl;
cout << "theVector's capacity is: " << theVector.capacity() << endl;

// Ensure there's room for at least 1000 elements.
theVector.reserve(1000);
cout << endl << "After reserving storage for 1000 elements:" << endl;
cout << "theVector's size is: " << theVector.size() << endl;
cout << "theVector's maximum size is: " << theVector.max_size()
<< endl;
cout << "theVector's capacity is: " << theVector.capacity() << endl;

// Ensure there's room for at least 2000 elements.
theVector.resize(2000);
cout << endl << "After resizing storage to 2000 elements:" << endl;
cout << "theVector's size is: " << theVector.size() << endl;
cout << "theVector's maximum size is: " << theVector.max_size()
<< endl;
cout << "theVector's capacity is: " << theVector.capacity() << endl;
}


Program Output is:


theVector's size is: 1
theVector's maximum size is: 1073741823
theVector's capacity is: 1

After reserving storage for 1000 elements:
theVector's size is: 1
theVector's maximum size is: 1073741823
theVector's capacity is: 1000

After resizing storage to 2000 elements:
theVector's size is: 2000
theVector's maximum size is: 1073741823
theVector's capacity is: 2000

> HI, when I try the following code, I get a segfault when compiled with
> VC.NET and g++ under cygwin.
>
> #1 vector<int> vi;
> #2 vector<int>::iterator ii = vi.begin();
> #3 vi.reserve(10);
> #4 for(int i = 0; i < 10; ++i) {
> #5 *ii++ = 4;
> #6 }
> #7 copy(vi.begin(), vi.end(), ostream_iterator<int>(cout, " "));
>
> Here is my break down on why this code should work (fill a vector with
> numbers, nevermind v[i] syntax, or v.push_back(), or the fill(...) stl
> function. I really wanted to know why the use of iterators causes a

problem
> here).
>
> #1 - v.size is 0;
> #2 - initiate a interator and point to v.begin().
> #3 - make space for 10 more elements, v.size() is still 0;
> #4-6 - loop and assign each space in the vector a number. #5 is where

segv
> happens.
>
> I was under the assumption that reserve will make space available to add
> more element, which the iterator will be able to walk through them. I'd
> appreciate any help on this issue.
>
> Smith
>
>
>
>
>



---
Posted via news://freenews.netfront.net
Complaints to
 
Reply With Quote
 
Jonathan Mcdougall
Guest
Posts: n/a
 
      07-25-2003
On Thu, 24 Jul 2003 23:36:37 -0400, "john smith"
<> wrote:

>HI, when I try the following code, I get a segfault when compiled with
>VC.NET and g++ under cygwin.
>
>#1 vector<int> vi;


This is an empty vector

>#2 vector<int>::iterator ii = vi.begin();


This is a valid iterator, but since the vector is empty, being() and
end() have the same value.

>#3 vi.reserve(10);


Two things : 1) These 10 new elements are not valid, _capacity_ and
_size_ are two different beasts. You increase the capacity with
reserve(), but you increase the size with, among others, push_back().

2) you just invalidated your iterator, because the location of the
elements may have changed (and they probably did).

>#4 for(int i = 0; i < 10; ++i) {
>#5 *ii++ = 4;


Undefined behavior, since the vector is still empty. Your application
may now crash at any time (or send some porn to your girlfriend`s
email address, you never know. C++ is quite polyvalent).

>#6 }
>#7 copy(vi.begin(), vi.end(), ostream_iterator<int>(cout, " "));


This would have worked if you did not try to dereference your
iterator. Nothing should have been printed on the screen, since the
vector is still empty.

>Here is my break down on why this code should work


It should'nt.

>(fill a vector with
>numbers, nevermind v[i] syntax, or v.push_back(), or the fill(...) stl
>function.


what?

> I really wanted to know why the use of iterators causes a problem
>here).


Because you try to access an empty vector.

>#1 - v.size is 0;


ok

>#2 - initiate a interator and point to v.begin().


ok

>#3 - make space for 10 more elements, v.size() is still 0;


that's it, you have the space for 10 elements, but it is illegal to
access these elements since they are not initialized. The only thing
you have here is raw memory. Do not try to access it.

>#4-6 - loop and assign each space in the vector a number. #5 is where segv
>happens.


>I was under the assumption that reserve will make space available to add
>more element, which the iterator will be able to walk through them. I'd
>appreciate any help on this issue.


std::vector::reserve() only increases the vector's capacity so that it
will avoid reallocation and it invalidates iterators. What's more,
these new elements are not valid elements, that is, you cannot access
them. The only reason for which you would want to use reserve() is to
avoid reallocation.

Jonathan

 
Reply With Quote
 
John Harrison
Guest
Posts: n/a
 
      07-25-2003

"john smith" <> wrote in message
news:bfq8gb$a55$...
> HI, when I try the following code, I get a segfault when compiled with
> VC.NET and g++ under cygwin.
>
> #1 vector<int> vi;
> #2 vector<int>::iterator ii = vi.begin();
> #3 vi.reserve(10);
> #4 for(int i = 0; i < 10; ++i) {
> #5 *ii++ = 4;
> #6 }
> #7 copy(vi.begin(), vi.end(), ostream_iterator<int>(cout, " "));
>
> Here is my break down on why this code should work (fill a vector with
> numbers, nevermind v[i] syntax, or v.push_back(), or the fill(...) stl
> function. I really wanted to know why the use of iterators causes a

problem
> here).
>
> #1 - v.size is 0;
> #2 - initiate a interator and point to v.begin().
> #3 - make space for 10 more elements, v.size() is still 0;
> #4-6 - loop and assign each space in the vector a number. #5 is where

segv
> happens.
>
> I was under the assumption that reserve will make space available to add
> more element,


Yes.

> which the iterator will be able to walk through them.


No. The only way to add elements to a vector is to change its size, for
instance by calling resize, push_back or insert

> I'd
> appreciate any help on this issue.
>
> Smith
>


reserve is just something you call for efficiency, it stops repeated
reallocations when you are adding multiple elements by using push_back or
insert. reserve also invalidates any iterators to the vector.

Here's how you should of done it.

vector<int> vi;
vi.resize(10);
copy(vi.begin(), vi.end(), ostream_iterator<int>(cout, " "));

john


 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off




Advertisments
 



1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57