0

I'm trying to pass the iterator to a separate function to then do something with the element at that location in the list.

This is not working for me.

#include <list>
#include <iostream>

using namespace std;

int main(int argc, char *argv[])
{
    void doSomething(iterator::<int> *it);

    list<int> intList;

    intList.push_back(10);
    intList.push_back(20);
    intList.push_back(10);
    intList.push_back(30);

    list<int>::iterator it;



    for (it = intList.begin(); it != intList.end(); it++)
    {
        if (*it == '10')
            doSomething(*it);
    };

    void doSomething(iterator <int> *it)
    {
        (*it) = 200;
    };
}
1
  • It is difficult to offer solutions when the problem statement is simply, "it doesn't work". Please edit your question to give a more complete description of what you expected to happen and how that differs from the actual results. See How to Ask for hints on what makes a good explanation. Commented May 5, 2016 at 9:43

4 Answers 4

3

iterator isn't a standalone type in itself. It's just a typedef (it could be more than that. But we may safely assume that for this question)

list<int>::iterator is a separate type and so is vector<int>::iterator without any common class in hierarchy. All functions that accept an iterator are typically templatized functions where the template type having the constraint to satisfy the requirements of iterator.

For your case you will have to declare doSomething as either:

void doSomething(list::iterator <int> it);  // will only work with std::list iterators

Or the way most STL functions/containers accept iterators

template<typename Iterator>
void doSomething(Iterator it); // generic. Will work with any container whose iterator has an overload for * operator

In either case at the caller side you can do

for (it = intList.begin(); it != intList.end(); it++)
{
    if (*it == 10)
       doSomething(it);
};
Sign up to request clarification or add additional context in comments.

Comments

1
  • itetator won't automatically mean iterator for std::list.
  • You cannot define functions inside functions: the GCC extension is only available for C, not for C++.
  • Match the types by using unary & operator (take address) and unary * operator (dereference).

Corrected code (at least it compiles):

#include <list>
#include <iostream>

using namespace std;

int main(int argc, char *argv[])
{
    void doSomething(list<int>::iterator *it);

    list<int> intList;

    intList.push_back(10);
    intList.push_back(20);
    intList.push_back(10);
    intList.push_back(30);

    list<int>::iterator it;

    for (it = intList.begin(); it != intList.end(); it++)
    {
        if (*it == '10')
            doSomething(&it);
    }

}

void doSomething(list<int>::iterator *it)
{
    *(*it) = 200;
}

To make this code better:

  • Declaring functions locally is not common.
  • Using reference might be better.
  • Using multi-character character constant looks weird. You may want simple integer 10 instead of '10', which may be 12592 (0x3130). Note that value of multi-character character constant is implementation-defined.

Code that seems better:

#include <list>
#include <iostream>

using namespace std;

 void doSomething(list<int>::iterator &it);

int main(int argc, char *argv[])
{

    list<int> intList;

    intList.push_back(10);
    intList.push_back(20);
    intList.push_back(10);
    intList.push_back(30);

    list<int>::iterator it;

    for (it = intList.begin(); it != intList.end(); it++)
    {
        if (*it == 10)
            doSomething(it);
    }

}

void doSomething(list<int>::iterator &it)
{
    (*it) = 200;
}

2 Comments

Passing an iterator by reference is redundant. The iterator is anyways a pointer behind the scenes.
And passing it as a mutable reference is really unnecessary.
0
#include <list>
#include <iostream>

using namespace std;

void doSomething(list<int>::iterator *it)
    {
        *(*it) = 200;
    }

int main(int argc, char *argv[])
{

    list<int> intList;

    intList.push_back(10);
    intList.push_back(20);
    intList.push_back(10);
    intList.push_back(30);

    list<int>::iterator it;



    for (it = intList.begin(); it != intList.end(); it++)
    {
        if (*it == '10')
            doSomething(&it);
    }   
}

Please make the doSomething function outside of main(). Also your argument in the function is wrong. iterator serves as a typedef and its kinda pointer in some way. You pass a ppointer as an argument , you need to take the address of your pointer with this symbol '&'.

Comments

0

Best-ish case use:

#include <list>

using namespace std;

template <typename T>
void doSomething(T it); /*Pre-condition: must be passed a dereferencible object.*/

int main(){
    list<int> intList;

    intList.push_back(10);
    intList.push_back(20);
    intList.push_back(10);
    intList.push_back(30);

    list<int>::iterator it;

    for (it = intList.begin(); it != intList.end(); it++){
        if (*it == 10) doSomething(it);
    }; 
}

template <typename T>
void doSomething(T it){
    (*it) = 200;
};

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.