您的位置:首页 > 其它

lambda

2016-02-06 23:35 543 查看
#include<functional>
#include<iostream>

std::function<int(int, int)> returnLambda()
{
return [](int x, int y) {
return x*y;
};
}

int main()
{
auto lf = returnLambda();
std::cout << lf(6, 7) << std::endl;
}


输出结果:42

lambda 与 bind对比

#include <functional>
#include <iostream>

int main()
{
auto plus10 = std::bind(std::plus<int>(),
std::placeholders::_1,
10);
std::cout << "+10:    " << plus10(7) << std::endl;

auto plus10times2 = std::bind(std::multiplies<int>(),
std::bind(std::plus<int>(),
std::placeholders::_1,
10),
2);
std::cout << "+10 *2: " << plus10times2(7) << std::endl;

auto pow3 = std::bind(std::multiplies<int>(),
std::bind(std::multiplies<int>(),
std::placeholders::_1,
std::placeholders::_1),
std::placeholders::_1);
std::cout << "x*x*x:  " << pow3(7) << std::endl;

auto inversDivide = std::bind(std::divides<double>(),
std::placeholders::_2,
std::placeholders::_1);
std::cout << "invdiv: " << inversDivide(49, 7) << std::endl;
}


#include <iostream>
int main()
{
auto plus10 = [](int i) {
return i + 10;
};
std::cout << "+10: " << plus10(7) << std::endl;
auto plus10times2 = [](int i) {
return (i + 10) * 2;
};
std::cout << "+10 *2: " << plus10times2(7) << std::endl;
auto pow3 = [](int i) {
return i*i*i;
};
std::cout << "x*x*x: " << pow3(7) << std::endl;
auto inversDivide = [](double d1, double d2) {
return d2 / d1;
};
std::cout << "invdiv: " << inversDivide(49, 7) << std::endl;
}


lambda与function objects

#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;

// function object to process the mean value
class MeanValue {
private:
long num;    // number of elements
long sum;    // sum of all element values
public:
// constructor
MeanValue () : num(0), sum(0) {
}

// "function call"
// - process one more element of the sequence
void operator() (int elem) {
++num;          // increment count
sum += elem;    // add value
}

// return mean value
double value () {
return static_cast<double>(sum) / static_cast<double>(num);
}
};

int main()
{
vector<int> coll = { 1, 2, 3, 4, 5, 6, 7, 8 };

// process and print mean value
MeanValue mv = for_each (coll.begin(), coll.end(),  // range
MeanValue());              // operation //for_each() has the unique ability to return its function object
cout << "mean value: " << mv.value() << endl;
}


#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;

int main()
{
vector<int> coll = { 1, 2, 3, 4, 5, 6, 7, 8 };

// process and print mean value
long sum = 0;
for_each(coll.begin(), coll.end(),  // range
[&sum](int elem) {
sum += elem;
});
double mv = static_cast<double>(sum) / static_cast<double>(coll.size());
cout << "mean value: " << mv << endl;
}


lambda与stateful function objects

#include <iostream>
#include <list>
#include <algorithm>
#include "print.hpp"
using namespace std;

class Nth {    // function object that returns true for the nth call
private:
int nth;       // call for which to return true
int count;     // call counter
public:
Nth (int n) : nth(n), count(0) {
}
bool operator() (int) {
return ++count == nth;
}
};

int main()
{
list<int> coll = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
PRINT_ELEMENTS(coll,"coll:        ");

// remove third element
list<int>::iterator pos;
pos = remove_if(coll.begin(),coll.end(),  // range
Nth(3));                  // remove criterion
coll.erase(pos,coll.end());

PRINT_ELEMENTS(coll,"3rd removed: ");
}


输出结果:

coll:        1 2 3 4 5 6 7 8 9 10

3rd removed: 1 2 4 5 7 8 9 10

#include <iostream>
#include <list>
#include <algorithm>
#include "print.hpp"
using namespace std;

int main()
{
list<int> coll = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
PRINT_ELEMENTS(coll,"coll:        ");

// remove third element
list<int>::iterator pos;
int count=0;     // call counter
pos = remove_if(coll.begin(),coll.end(),   // range
[count] (int) mutable {   // remove criterion
return ++count == 3;
});
coll.erase(pos,coll.end());

PRINT_ELEMENTS(coll,"3rd removed: ");
}


coll: 1 2 3 4 5 6 7 8 9 10

3rd removed: 1 2 4 5 7 8 9 10

If you pass the argument by reference and don’t use mutable, the behavior is as expected,

because both lambda objects internally used by remove_if() share the same state. Thus, with

the following:

int count=0; // call counter
pos = remove_if(coll.begin(),coll.end(), // range
[&count] (int) { // remove criterion
return ++count == 3;
});


the output is:

coll: 1 2 3 4 5 6 7 8 9 10

3rd removed: 1 2 4 5 6 7 8 9 10

#include <iostream>
#include <algorithm>
#include <functional>
#include <locale>
#include <string>
using namespace std;
using namespace std::placeholders;

char myToupper (char c)
{
std::locale loc;
return std::use_facet<std::ctype<char> >(loc).toupper(c);
}

int main()
{
string s("Internationalization");
string sub("Nation");

// search substring case insensitive
string::iterator pos;
pos = search (s.begin(),s.end(),           // string to search in
sub.begin(),sub.end(),       // substring to search
bind(equal_to<char>(),       // compar. criterion
bind(myToupper,_1),
bind(myToupper,_2)));
if (pos != s.end()) {
cout << "\"" << sub << "\" is part of \"" << s << "\""
<< endl;
}
}

#include <iostream>
#include <algorithm>
#include <locale>
#include <string>
using namespace std;

char myToupper (char c)
{
std::locale loc;
return std::use_facet<std::ctype<char> >(loc).toupper(c);
}

int main()
{
string s("Internationalization");
string sub("Nation");

// search substring case insensitive
string::iterator pos;
pos = search (s.begin(),s.end(),           // string to search in
sub.begin(),sub.end(),       // substring to search
[] (char c1, char c2) {      // compar. criterion
return myToupper(c1)==myToupper(c2);
});
if (pos != s.end()) {
cout << "\"" << sub << "\" is part of \"" << s << "\""
<< endl;
}
}

calling member functions

#include <functional>
#include <algorithm>
#include <vector>
#include <iostream>
#include <string>
using namespace std;
using namespace std::placeholders;

class Person {
private:
string name;
public:
Person (const string& n) : name(n) {
}
void print () const {
cout << name << endl;
}
void print2 (const string& prefix) const {
cout << prefix << name << endl;
}
//...
};

int main()
{
vector<Person> coll
= { Person("Tick"), Person("Trick"), Person("Track") };

// call member function print() for each person
for_each (coll.begin(), coll.end(),
bind(&Person::print,_1));
cout << endl;

// call member function print2() with additional argument for each person
for_each (coll.begin(), coll.end(),
bind(&Person::print2,_1,"Person: "));
cout << endl;

// call print2() for temporary Person
bind(&Person::print2,_1,"This is: ")(Person("nico"));
}

#include <functional>
#include <algorithm>
#include <vector>
#include <iostream>
#include <string>
using namespace std;
using namespace std::placeholders;

class Person {
private:
string name;
public:
Person(const string& n) : name(n) {
}
void print() const {
cout << name << endl;
}
void print2(const string& prefix) const {
cout << prefix << name << endl;
}
//...
};

int main()
{
vector<Person> coll
= { Person("Tick"), Person("Trick"), Person("Track") };

// call member function print() for each person
for_each(coll.begin(), coll.end(),
[](const Person& p) {
p.print();
});
cout << endl;

// call member function print2() with additional argument for each person
for_each(coll.begin(), coll.end(),
[](const Person& p) {
p.print2("Person: ");
});
}


Using lambdas as hash function and equivalence criterion

//print.hpp
#include <iostream>
#include <string>

// PRINT_ELEMENTS()
// - prints optional string optstr followed by
// - all elements of the collection coll
// - in one line, separated by spaces
template <typename T>
inline void PRINT_ELEMENTS(const T& coll,
const std::string& optstr = "")
{
std::cout << optstr;
for (const auto& elem : coll) {
std::cout << elem << ' ';
}
std::cout << std::endl;
}


//hashval.hpp
#pragma once
#include <functional>

// from boost (functional/hash):
// see http://www.boost.org/doc/libs/1_35_0/doc/html/hash/combine.html template <typename T>
inline void hash_combine(std::size_t& seed, const T& val)
{
seed ^= std::hash<T>()(val) + 0x9e3779b9 + (seed << 6) + (seed >> 2);
}

// auxiliary generic functions to create a hash value using a seed
template <typename T>
inline void hash_val(std::size_t& seed, const T& val)
{
hash_combine(seed, val);
}
template <typename T, typename... Types>
inline void hash_val(std::size_t& seed,
const T& val, const Types&... args)
{
hash_combine(seed, val);
hash_val(seed, args...);
}

// auxiliary generic function to create a hash value out of a heterogeneous list of arguments
template <typename... Types>
inline std::size_t hash_val(const Types&... args)
{
std::size_t seed = 0;
hash_val(seed, args...);
return seed;
}

//main.cpp
#include <string>
#include <iostream>
#include <unordered_set>
#include "hashval.hpp"
#include <functional>
#include "print.hpp"
using namespace std;

class Customer {
private:
string fname;
string lname;
long   no;
public:
Customer(const string& fn, const string& ln, long n)
: fname(fn), lname(ln), no(n) {
}
string firstname() const {
return fname;
};
string lastname() const {
return lname;
};
long number() const {
return no;
};
friend ostream& operator << (ostream& strm, const Customer& c) {
return strm << "[" << c.fname << "," << c.lname << "," << c.no << "]";
}
};

int main()
{
// lambda for user-defined hash function
auto hash = [](const Customer& c) {
return hash_val(c.firstname(), c.lastname(), c.number());
};

// lambda for user-defined equality criterion
auto eq = [](const Customer& c1, const Customer& c2) {
return c1.number() == c2.number();
};

// create unordered set with user-defined behavior
unordered_set<Customer, decltype(hash), decltype(eq)> custset(10, hash, eq);
// ERROR: unordered_set<Customer,function<size_t(Customer,Customer)>,decltype(eq)> custset(10,hash,eq);

custset.insert(Customer("nico", "josuttis", 42));
PRINT_ELEMENTS(custset);

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: