CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Results 1 to 6 of 6
  1. #1
    Join Date
    Feb 2009
    Location
    Ukraine
    Posts
    64

    std::vector's push_back() segfaults - very weird

    Hi All,

    I have been persuaded for a long time that stl containers are the better choice compared to any home-cooked alternatives, partially, because experienced that in my own practice.
    One thing that is attractive, if I'm not even very concerned about speed, is that I do not have to bother about allocs/reallocs/frees almost all the time - in the terms of container usage. But recently I met strange thing.
    Suppose, you emulate multidimensional arrays with std::vector - for 3 dimensions. The first two dimensions are assumed to hold comparably large number of elements, so I bother a bit about optimization and use reserve() for them. But the last dimension is assumed to hold just a couple of elements, and it initially has zero-size. For inserting an element to the last dimension vector, I use push_back() - since it dynamically changes size() and reserves some capacity() for potential future insertions. That looks like
    Code:
    typedef vector< vector < vector <X> > > MyContainer;
    MyContainer c;
    // ... get some info about 1st dimension size into s1
    c.reserve(s1);
    // ...
    unsigned int i = 0;
    // ... get some info about 2nd dimension size into s2
    c[i].reserve(s2);
    // ...
    unsigned int j = 0;
    // ... init an X in x
    c[i][j].push_back(x);
    All is to work fine, isn't it? But, for my disaster, when push_back() is called again and again for the 5th time for example, it segfaults...
    But, if I do reserve() at least 10 elements for the third dimesion, all works fine.
    Could someone clarify the problem if it exists? I even tend to blame std::vector for that unexpected behavior...

  2. #2
    Join Date
    Aug 2000
    Location
    West Virginia
    Posts
    7,721

    Re: std::vector's push_back() segfaults - very weird

    see my added comments

    Code:
    	MyContainer c;
    	// ... get some info about 1st dimension size into s1
    	c.reserve(s1);
    	// ...
    	unsigned int i = 0;
    	// ... get some info about 2nd dimension size into s2
    	c[i].reserve(s2);  // c[i] does not exist
    	// ...
    	unsigned int j = 0;
    	// ... init an X in x
    	c[i][j].push_back(x);  // c[i][j] does not exist

  3. #3
    Join Date
    Jan 2006
    Location
    Singapore
    Posts
    6,765

    Re: std::vector's push_back() segfaults - very weird

    That seems a little weird. Why not post the smallest and simplest compilable program that demonstrates the problem?

    EDIT:
    Oh yeah, if you did not actually push_back() in the omitted portions, then Philip Nicoletti's points look valid.
    C + C++ Compiler: MinGW port of GCC
    Build + Version Control System: SCons + Bazaar

    Look up a C/C++ Reference and learn How To Ask Questions The Smart Way
    Kindly rate my posts if you found them useful

  4. #4
    Join Date
    Apr 1999
    Posts
    27,449

    Re: std::vector's push_back() segfaults - very weird

    Quote Originally Posted by AmadeusAD View Post
    The first two dimensions are assumed to hold comparably large number of elements, so I bother a bit about optimization and use reserve() for them.
    You should learn the difference between vector::reserve() and vector::resize(). That is where your mistake occurs.

    The reserve() function only does that -- reserves the memory so that future calls to push_back(), insert(), resize() etc. do not incur the overhead of reallocation.

    The resize() actually says "I am now giving this vector 'n' logical elements", where "n" is the number of elements that the vector can logically hold, i.e, the indices of the vector are valid from 0 to n-1. I say "logically" in that reality, the vector has usually more memory in reserve, but can only logically access "n" of them.

    Regards,

    Paul McKenzie

  5. #5
    Join Date
    Feb 2009
    Location
    Ukraine
    Posts
    64

    Re: std::vector's push_back() segfaults - very weird

    In my original working code, I have the vector resized after reserve(), so all the elements before push_back() exist.
    About small compilable program - you know, I reproduced the same (I think so) situation in just a main(), as close to the original as possible, but it worked flawlessly... I do not know what happens there in my working code. Probably, as it is much more complicated, I have missed something and there happens stack corruption or something like that... I decided that for a couple of elements lists will do, even if I want 'random' access.

    P.S. Anyway, after surfing the web, I discovered quite a large number of topics devoted to the same problem: std::vector's push_back(), reserve() and so on, but disasterously, there is no clear problem reason anywhere, just suggested alternatives... Hope somebody knows the clue.

  6. #6
    Join Date
    Jan 2006
    Location
    Singapore
    Posts
    6,765

    Re: std::vector's push_back() segfaults - very weird

    Quote Originally Posted by AmadeusAD
    In my original working code, I have the vector resized after reserve(), so all the elements before push_back() exist.
    In that case, why bother reserving at all? You might as well resize immediately.

    Quote Originally Posted by AmadeusAD
    About small compilable program - you know, I reproduced the same (I think so) situation in just a main(), as close to the original as possible, but it worked flawlessly... I do not know what happens there in my working code. Probably, as it is much more complicated, I have missed something and there happens stack corruption or something like that.
    I suppose the next best thing is to post the relevant part of your actual code.
    C + C++ Compiler: MinGW port of GCC
    Build + Version Control System: SCons + Bazaar

    Look up a C/C++ Reference and learn How To Ask Questions The Smart Way
    Kindly rate my posts if you found them useful

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  





Click Here to Expand Forum to Full Width

Featured