predicate specified directly into STL algo call - Codeblocks

hi there,
i have a question about this interesting "lambda" facility which i guess is not supported by my current codeblock version (which does not yet support c++11):

std::cout << std::count_if(vec.begin(),vec.end(),[](int n){return n%2==0;}) << std::endl;


i believe this is a feature available in visual studio... Has anybody using codeblocks found an alternative way to do something similar, or is it just not possible??

At the moment, i cannot find anything better than:

//....
bool even(int n)
{
    return n%2==0;
}
int main()
{
     //....
     std::cout << std::count_if(vec.begin(),vec.end(),even) << std::endl;
     //....
}


any hint appreciated. thanks
At the moment, i cannot find anything better than:


does this work? I'm not sure how it does in the way you've 'called' your even function.
mutexe wrote:
does this work? I'm not sure how it does in the way you've 'called' your even function.

The third argument of the count_if call is a pointer to the predicate function.
Last edited on
yes i know, but there's no parameter to pass in his example.

I am aware that his first quote will work on c++11, i was commenting on his second one.
there's no parameter to pass in his example.

std::count_if calls its third argument using a function-call expression, passing the dereferenced iterator as the argument of that function call: whether it's a lambda, a function pointer, a user-defined functor or a library-defined functor doesn't matter

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
#include <algorithm>
#include <vector>
#include <iostream>
#include <functional>
#include <ext/functional>
#include <boost/phoenix/core.hpp>
#include <boost/phoenix/operator.hpp>

bool even(int n) { return n%2==0; }
int main()
{
    // note: must be defined at file scope before C++11
    struct Even {
        bool operator()(int n) const {
            return n%2==0;
        }
    };


    std::vector<int> vec = {1,2,3,4,5,6,7};

    // pointer to function (could also write &even to be explicit)
    std::cout << std::count_if(vec.begin(),vec.end(), even) << '\n';

    // user-defined function object
    std::cout << std::count_if(vec.begin(),vec.end(), Even() ) << '\n';

    // STL (using one of the parts that didn't make it into C++)
    std::cout << std::count_if(vec.begin(),vec.end(),
                  __gnu_cxx::compose1(
                       std::bind2nd(std::equal_to<int>(),0),
                       std::bind2nd(std::modulus<int>(),2)
                   )
                 ) << '\n';

    // C++11 lambda
    std::cout << std::count_if(vec.begin(),vec.end(),
                               [](int n){return n%2==0;}) << '\n';

    // boost.phoenix (replaced boost.lambda)
    using boost::phoenix::arg_names::arg1;
    std::cout << std::count_if(vec.begin(),vec.end(), arg1%2 == 0 );
}



demo: http://coliru.stacked-crooked.com/a/247cbc2afe412203

PS: don't know what works in C::B, never used it.
Last edited on
yep. sorry, i'm half asleep again.
> At the moment, i cannot find anything better than:
Ignoring the need to give it a name, ┬┐what's the problem with that solution?


> which i guess is not supported by my current codeblock version (which does not yet support c++11):
update your compiler (gcc>=4.8.2, clang>=3.4)
Last edited on
ne555, no problem in using it, as long as it works. It's just the lambda thing seems quite useful in writing inline simple functions, and i guess improving readabilty too
thanks Cubbi, this works in Codeblocks too:

// STL (using one of the parts that didn't make it into C++)
    std::cout << std::count_if(vec.begin(),vec.end(),
                  __gnu_cxx::compose1(
                       std::bind2nd(std::equal_to<int>(),0),
                       std::bind2nd(std::modulus<int>(),2)
                   )
                 ) << '\n';


C::B shouldn't ship with that old a version of GCC/MinGW...

Make sure to go to Settings --> Compiler --> Compiler Flags and enable the C++11 stuff.

Then you shouldn't have any trouble using lambdas.

Hope this helps!

[edit]
BTW, using the standalone function is better than the hideous GCC internal stuff, IMHO.
Last edited on
I just posted that choice to show how painfully this was done in STL
I don't think people typically appreciate a lot of the magic that goes into making the STL and other high-level constructs we use in C++ so convenient...
@Duoas I'm not trying to show any magic, but rather the evolution of the standard library, from 1994 STL's compose1(bind2nd,bind2nd) to boost's and C++11's rather more convenient lambdas.
Last edited on
You misread me. I mean that people are generally oblivious, not disdainful.
thanks Duoas,

Make sure to go to Settings --> Compiler --> Compiler Flags and enable the C++11 stuff.


i tried but still no luck. The 'Build' ignores anything done/saved after ticking the c++11 option, it just builds everything that was there until i made that change...

Anyway, thanks for the tip, i'll retry and probably will need to install a more recent version
Topic archived. No new replies allowed.