Trouble with vector::iterator

Discussion in 'C++' started by Prasad, Nov 19, 2008.

  1. Prasad

    Prasad Guest

    Hi,

    I have been using vector::iterators for a while now. This is the first
    time I have encountered this problem.
    The vector contains one element.

    1. vector<GroupSetTemplate>::iterator gstIt;
    2. for(gstIt= this->invariantState.getGroupSetTemplates().begin();
    gstIt!=this->invariantState.getGroupSetTemplates().end();gstIt++)
    3{
    4 cout<<"Gst name"<<(*gstIt).getName()<<endl;
    5}

    Line 4 throws me segmentation fault.

    However if I rewrite the above code using vector::at() it works fine.
    GroupSetTemplate element = invariantState.getGroupSetTemplates().at
    (0);
    cout<<"Gst name"<<element.getName()<<endl;

    So I know that there is no problem with the element. Am I missing
    something ?
    Prasad, Nov 19, 2008
    #1
    1. Advertising

  2. Prasad wrote:
    > I have been using vector::iterators for a while now. This is the first
    > time I have encountered this problem.
    > The vector contains one element.
    >
    > 1. vector<GroupSetTemplate>::iterator gstIt;
    > 2. for(gstIt= this->invariantState.getGroupSetTemplates().begin();
    > gstIt!=this->invariantState.getGroupSetTemplates().end();gstIt++)
    > 3{
    > 4 cout<<"Gst name"<<(*gstIt).getName()<<endl;
    > 5}
    >
    > Line 4 throws me segmentation fault.
    >
    > However if I rewrite the above code using vector::at() it works fine.
    > GroupSetTemplate element = invariantState.getGroupSetTemplates().at
    > (0);
    > cout<<"Gst name"<<element.getName()<<endl;
    >
    > So I know that there is no problem with the element. Am I missing
    > something ?


    No, you don't know if there's a problem with the element. In your second
    version (with 'at') you create a _copy_ of the vector element, while in
    the first version you access the vector element itself. The process of
    creating a copy can possibly masquerade the existing problem with the
    vector element. Try this

    GroupSetTemplate& element =
    invariantState.getGroupSetTemplates().at(0);
    cout << "Gst name" << element.getName() << endl;

    (note the use of reference) and see if it works fine or also throws a
    segfault. This would be a better test, compared to your version with a copy.

    Otherwise, the code you provided looks fine. The problem must be elsewhere.

    --
    Best regards,
    Andrey Tarasevich
    Andrey Tarasevich, Nov 19, 2008
    #2
    1. Advertising

  3. Prasad

    Salt_Peter Guest

    On Nov 18, 7:17 pm, Prasad <> wrote:
    > Hi,
    >
    > I have been using vector::iterators for a while now. This is the first
    > time I have encountered this problem.
    > The vector contains one element.
    >
    > 1. vector<GroupSetTemplate>::iterator gstIt;
    > 2. for(gstIt= this->invariantState.getGroupSetTemplates().begin();
    > gstIt!=this->invariantState.getGroupSetTemplates().end();gstIt++)
    > 3{
    > 4 cout<<"Gst name"<<(*gstIt).getName()<<endl;
    > 5}
    >
    > Line 4 throws me segmentation fault.
    >
    > However if I rewrite the above code using vector::at() it works fine.
    > GroupSetTemplate element = invariantState.getGroupSetTemplates().at
    > (0);
    > cout<<"Gst name"<<element.getName()<<endl;
    >
    > So I know that there is no problem with the element. Am I missing
    > something ?


    As already noted, at(0) returns a copy. Your original code involves
    iterators. Lets bet member function getGroupSetTemplates() returns a
    local variable (hence the seg fault).

    The fact that you have a conditional expression in that for loop like
    so:

    gstIt!=this->invariantState.getGroupSetTemplates().end()

    is indicative of poor programming practices.
    You could always try a simplified reconstruction of your class
    hierarchy and post a short, compilable snippet.
    Salt_Peter, Nov 19, 2008
    #3
  4. Prasad

    James Kanze Guest

    On Nov 19, 4:09 am, Salt_Peter <> wrote:
    > On Nov 18, 7:17 pm, Prasad <> wrote:
    > > I have been using vector::iterators for a while now. This is
    > > the first time I have encountered this problem.
    > > The vector contains one element.


    > > 1. vector<GroupSetTemplate>::iterator gstIt;
    > > 2. for(gstIt= this->invariantState.getGroupSetTemplates().begin();
    > > gstIt!=this->invariantState.getGroupSetTemplates().end();gstIt++)
    > > 3{
    > > 4 cout<<"Gst name"<<(*gstIt).getName()<<endl;
    > > 5}


    > > Line 4 throws me segmentation fault.


    > > However if I rewrite the above code using vector::at() it works fine.
    > > GroupSetTemplate element = invariantState.getGroupSetTemplates().at
    > > (0);
    > > cout<<"Gst name"<<element.getName()<<endl;


    > > So I know that there is no problem with the element. Am I
    > > missing something ?


    > As already noted, at(0) returns a copy.


    No. The function vector<>::at() returns a reference. He makes
    the copy afterwards.

    > Your original code involves iterators. Lets bet member
    > function getGroupSetTemplates() returns a local variable
    > (hence the seg fault).


    Returns a local variable, or returns a reference to a local
    variable. Either could certainly explain his symptoms. (So
    could a few other things, but that sounds like a pretty good
    guess.)

    > The fact that you have a conditional expression in that for
    > loop like so:


    > gstIt!=this->invariantState.getGroupSetTemplates().end()


    > is indicative of poor programming practices.


    Why? I'd say it was more or less standard practice. In fact, a
    for loop without a conditional expression would be an endless
    loop. (It's not standard practice to consistently write out the
    this->, of course, but maybe this code is in a template, and
    invariantState is a member of a dependent base class.)

    --
    James Kanze (GABI Software) email:
    Conseils en informatique orientée objet/
    Beratung in objektorientierter Datenverarbeitung
    9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
    James Kanze, Nov 19, 2008
    #4
  5. Prasad

    Prasad Guest

    On Nov 19, 3:33 am, James Kanze <> wrote:
    > On Nov 19, 4:09 am, Salt_Peter <> wrote:
    >
    >
    >
    > > On Nov 18, 7:17 pm, Prasad <> wrote:
    > > > I have been using vector::iterators for a while now. This is
    > > > the first time I have encountered this problem.
    > > > The vector contains one element.
    > > > 1. vector<GroupSetTemplate>::iterator gstIt;
    > > > 2. for(gstIt= this->invariantState.getGroupSetTemplates().begin();
    > > > gstIt!=this->invariantState.getGroupSetTemplates().end();gstIt++)
    > > > 3{
    > > >  4            cout<<"Gst name"<<(*gstIt).getName()<<endl;
    > > > 5}
    > > > Line 4 throws me segmentation fault.
    > > > However if I rewrite the above code using vector::at() it works fine.
    > > > GroupSetTemplate element = invariantState.getGroupSetTemplates().at
    > > > (0);
    > > > cout<<"Gst name"<<element.getName()<<endl;
    > > > So I know that there is no problem with the element. Am I
    > > > missing something ?

    > > As already noted, at(0) returns a copy.

    >
    > No. The function vector<>::at() returns a reference.  He makes
    > the copy afterwards.
    >
    > > Your original code involves iterators. Lets bet member
    > > function getGroupSetTemplates() returns a local variable
    > > (hence the seg fault).

    >
    > Returns a local variable, or returns a reference to a local
    > variable.  Either could certainly explain his symptoms.  (So
    > could a few other things, but that sounds like a pretty good
    > guess.)


    getGroupSetTemplates() returns a class member. Is that a problem?


    >
    > > The fact that you have a conditional expression in that for
    > > loop like so:
    > > gstIt!=this->invariantState.getGroupSetTemplates().end()
    > > is indicative of poor programming practices.

    >
    > Why?  I'd say it was more or less standard practice.  In fact, a
    > for loop without a conditional expression would be an endless
    > loop.  (It's not standard practice to consistently write out the
    > this->, of course, but maybe this code is in a template, and
    > invariantState is a member of a dependent base class.)
    >
    > --
    > James Kanze (GABI Software)             email:
    > Conseils en informatique orientée objet/
    >                    Beratung in objektorientierter Datenverarbeitung
    > 9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
    Prasad, Nov 20, 2008
    #5
  6. Prasad wrote:
    > getGroupSetTemplates() returns a class member. Is that a problem?


    What does "returns a class member" mean? Does it return a copy of a
    class member? Or does it return a reference to a class member? It is a
    problem if the former is true.

    Did you make a test with 'at' and reference?

    --
    Best regards,
    Andrey Tarasevich
    Andrey Tarasevich, Nov 20, 2008
    #6
  7. Prasad

    Prasad Guest

    On Nov 19, 8:06 pm, Andrey Tarasevich <>
    wrote:
    > Prasad wrote:
    > > getGroupSetTemplates() returns a class member. Is that a problem?

    >
    > What does "returns a class member" mean? Does it return a copy of a
    > class member? Or does it return a reference to a class member? It is a
    > problem if the former is true.
    >
    > Did you make a test with 'at' and reference?
    >
    > --
    > Best regards,
    > Andrey Tarasevich


    Yes. The test with reference fails too. Any reason why the exact same
    calls fail for reference but work for the copy?
    Infact a valgrind analysis revealed a problem with string access,
    which is in one of the innermost classes.

    ==32069== Process terminating with default action of signal 11
    (SIGSEGV)
    ==32069== Access not within mapped region at address 0xFFFFFFFC
    ==32069== at 0x40CCD3A: std::string::string(std::string const&)
    (in /usr/lib/libstdc++.so.6.0.9)

    Any idea what this error means? AFAIK I am returning any local
    references or variables.

    ~Prasad
    Prasad, Nov 20, 2008
    #7
  8. Prasad

    Prasad Guest

    On Nov 19, 8:06 pm, Andrey Tarasevich <>
    wrote:
    > Prasad wrote:
    > > getGroupSetTemplates() returns a class member. Is that a problem?

    >
    > What does "returns a class member" mean? Does it return a copy of a
    > class member? Or does it return a reference to a class member? It is a
    > problem if the former is true.


    I was able to fix the problem.
    //Original code
    vector<GroupSetTemplates> getGroupSetTemplates()
    {
    return this->groupSetTemplates;
    }

    //Fixed code
    vector<GroupSetTemplates>& getGroupSetTemplates()
    {
    return this->groupSetTemplates;
    }

    My understanding of this is
    1. Initially a copy of groupSetTemplates was being returned. I was
    getting an error because I was creating an iterator over returned
    copy.
    2. I am returning a reference of groupSetTemplates. A copy of the
    reference is returned which still points to original groupSetTemplate
    and hence my code works fine.

    Is this understanding correct?
    >
    > Did you make a test with 'at' and reference?
    >
    > --
    > Best regards,
    > Andrey Tarasevich
    Prasad, Nov 20, 2008
    #8
  9. Prasad

    Prasad Guest

    On Nov 20, 12:41 am, Paavo Helde <> wrote:
    > Prasad <> kirjutas:
    >
    >
    >
    > > On Nov 19, 8:06 pm, Andrey Tarasevich <>
    > > wrote:
    > >> Prasad wrote:
    > >> > getGroupSetTemplates() returns a class member. Is that a problem?

    >
    > >> What does "returns a class member" mean? Does it return a copy of a
    > >> class member? Or does it return a reference to a class member? It is a
    > >> problem if the former is true.

    >
    > > I was able to fix the problem.
    > > //Original code
    > > vector<GroupSetTemplates> getGroupSetTemplates()
    > > {
    > > return this->groupSetTemplates;
    > > }

    >
    > > //Fixed code
    > > vector<GroupSetTemplates>& getGroupSetTemplates()
    > > {
    > > return this->groupSetTemplates;
    > > }

    >
    > > My understanding of this is
    > > 1. Initially a copy of groupSetTemplates was being returned. I was
    > > getting an error because I was creating an iterator over returned
    > > copy.

    >
    > The problem was that you returned two copies of groupSetTemplates, and
    > you were attempting to iterate from the beginning of the first to the end
    > of the second.
    >
    > > 2. I am returning a reference of groupSetTemplates. A copy of the
    > > reference is returned which still points to original groupSetTemplate
    > > and hence my code works fine.

    >
    > > Is this understanding correct?

    >
    > Basically yes, this is what Andray has tried to talk you.
    >
    > Terminological note: usually one does not talk about a "copy of a
    > reference" (though there might be some copying of bits involved in the
    > CPU level, but this is irrelevant). If the function returns a reference,
    > it just returns a reference.
    >
    > Paavo


    Thanks Paavo and Andray :)
    Prasad, Nov 20, 2008
    #9
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. pmatos
    Replies:
    6
    Views:
    23,778
  2. Replies:
    8
    Views:
    1,913
    Csaba
    Feb 18, 2006
  3. Javier
    Replies:
    2
    Views:
    558
    James Kanze
    Sep 4, 2007
  4. zl2k
    Replies:
    27
    Views:
    1,575
    Francesco S. Carta
    Sep 7, 2010
  5. Rushikesh Joshi
    Replies:
    0
    Views:
    356
    Rushikesh Joshi
    Jul 10, 2004
Loading...

Share This Page