I want to pass a struct implementing operator() in to a function that accepts boost::function. This struct keeps track of the number of times it's been called.

struct CallCounter
{
    CallCounter() : count( 0 ) {}
    void operator()()
    {
        // do stuff
        cout << "count is at " << count << endl;
        ++count;
    }

    int count;
};

However, when I try to access count after passing it to another function, count is still at 0.

void callNTimes( int n, boost::function<void()> func )
{
    for ( int i = 0; i < n; ++i )
        func();
}

int main()
{
    CallCounter counter;
    callNTimes( 20, counter );

    cout << counter.count << endl; // prints 0
    return 0;
}

Even though while counter is being called, it's printing out the correct count. I understand that boost::function is making a copy of my struct counter. Is there a way to pass it by reference so that afterwards, count is the right number?

有帮助吗?

解决方案

The boost function stuff takes variables by value by default, much like normal functions. If you want the function to use a reference to your CallCounter, you have to tell it that explicitly:

callNTimes( 20, boost::ref(counter) );

See it here: http://coliru.stacked-crooked.com/a/5843b6dde685b569

There also exists a boost::cref if you want a constant reference, but no boost::rref (which would be nearly identical to a value, but single use. function is multi-use, so no moves). Additionally, as of C++11, all of this is also in the std namespace.

In addition, Jefffrey's suggestion is generally considered a better way to code this sort of thing, if possible. It can have a negative impact on compile times though.

其他提示

I see that you are using boost::function. It's actually not necessary here, you can just use templates and pass the functor by reference:

template<typename Functor>
void callNTimes( int n, Functor& func )
{
    for ( int i = 0; i < n; ++i )
        func();
}

Live demo

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top