C++ファンクタとは関数のように扱えるインスタンスです。以下のコードは最も簡単なファンクタです。
|
#include <iostream> using namespace std; class SimpleFunctor { public: void operator()() { cout << "Hello" << endl; } }; int main() { SimpleFunctor simpleFunctor; simpleFunctor(); return 0; } |
以下のコードはintを引数とするファンクタです。vectorに対してfor_eachを使ってすべての要素に対して、ファンクタをコールしています。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24
|
#include <iostream> #include <vector> #include <algorithm> using namespace std; class IntFunctor { public: void operator()(int i) { cout << "Hello" << i << endl; } }; int main() { IntFunctor intFunctor; intFunctor(10); vector<int> vi; vi.push_back(123); vi.push_back(456); for_each(vi.begin(), vi.end(), intFunctor); return 0; } |
以下のコードはstd::bindを使って、ファンクタを作成しています。
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
|
#include <functional> #include <vector> #include <algorithm> using namespace std; void testfunc(int i1, int i2) { printf("%d %d\n", i1, i2); } int main() { // testfuncの第一引数、第二引数ともにfuncの引数を渡す。 auto func0 = bind(testfunc, std::placeholders::_1, std::placeholders::_2); func0(100, 101); // testfuncの第一引数に9999を渡し、第二引数にはfuncの引数を渡す。 auto func1 = bind(testfunc, 9999, std::placeholders::_1); func1(100); // testfuncの第一引数にviの要素を渡し、第二引数には7777を渡す。 vector<int> vi = { 123, 345, 567 }; auto func2 = bind(testfunc, std::placeholders::_1, 7777); for_each(vi.begin(), vi.end(), func2); return 0; } |
以下のコードは多段にファンクタを作っています。このように引数を減らすことをカリー化といいます。
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
|
#include <iostream> #include <functional> using namespace std; void testfunc(int i1, int i2, int i3, int i4, int i5) { cout << i1 << " " << i2 << " " << i3 << " " << i4 << " " << i5 << endl; } int main() { auto f1 = bind(testfunc, 1, placeholders::_1, placeholders::_2, placeholders::_3, placeholders::_4); auto f2 = bind(f1, 2, placeholders::_1, placeholders::_2, placeholders::_3); auto f3 = bind(f2, 3, placeholders::_1, placeholders::_2); auto f4 = bind(f3, 4, placeholders::_1); f4(5); // prints "1 2 3 4 5" return 0; } |