Bug in select_many when predicate return empty range?

Jan 29, 2015 at 6:07 AM
New to cpplinq (just found it today), but it looks like exactly what I need to do some data crunching.

I think I may have found a bug with select_many when the predicate returns an empty range. I've included a possible fix below as well.

Consider the following code:
auto r = range(0, 3)
  >> select_many([](int idx) { return range(0, idx); })
  >> to_vector();

for(auto cur : r) cout << cur << endl;
I would expect the output would be:
0
0
1
0
1
2
With the current version of cpplinq.hpp this code instead produces no output and the predicate only gets called once. The empty range generated in the call to range(0,0) is causing processing to terminate.

The fix is to change select_many_range::next to continue even when one of the child ranges is empty. The current body of this function is:
CPPLINQ_INLINEMETHOD bool next ()
{
    if (inner_range && inner_range->next ())
    {
        return true;
    }

    if (range.next ())
    {
        inner_range = predicate (range.front ());
        return inner_range && inner_range->next ();
    }

    inner_range.clear ();

    return false;
}
I think the function should actually be:
CPPLINQ_INLINEMETHOD bool next ()
{
    if (inner_range && inner_range->next ())
    {
        return true;
    }

    while (range.next ())
    {
        inner_range = predicate (range.front ());
        if (inner_range && inner_range->next ()) 
        {
          return true;
        }
    }

    return false;
}
Coordinator
Jan 30, 2015 at 4:15 PM
Can you make a Pull Request of this and add unit tests.

Makes it easier to review and merge.