引入
先看一段不用for_each 的代码:
#include
#include
#include
using namespace std; int main() { int a[] = { 1, 2, 3, 4}; vector<int> v(a, a+sizeof(a)/sizeof(int)); for(vector<int>::iterator itor = v.begin();itor!=v.end();++itor) { cout<<*itor<
其中这句代码:
for(vector<int>::iterator itor = v.begin();itor!=v.end();++itor)
略长,如果不常写,倒是很容易手生。
template<typename InputIterator, typename Function> Function for_each(InputIterator beg, InputIterator end, Function f) { while(beg != end) f(*beg++); }
由以上source可知,for_each()只能配合global function和function object。
以下将对procedure based、object oriented、generics三种paradigm与for_each()搭配做探讨。
Procedure Based与for_each()搭配
1、不传入参数
void fun(int i ) { cout<
int main() {
int a[] = {
1,
2,
3,
4};
vector<int> v(a, a+
sizeof(a)/
sizeof(
int)); for_each(v.begin(), v.end(), fun); }
2、传入参数
要传入参数给global function ,需要使用 ptr_fun() 这个 function adapter 将global function 转成function object , 然后再用bind2nd() 将参数bind成一个function object。(这句话好拗口)。
void fun(int i, const char* str) { cout<
int main() {
int a[] = {
1,
2,
3,
4};
vector<int> v(a, a+
sizeof(a)/
sizeof(
int)); for_each(v.begin(), v.end(), bind2nd(ptr_fun(fun),
"Element:")); }
Object Oriented 与for_each 搭配
1、不传入参数,使用function object
#include
#include
#include
#include
using namespace std; struct Play { void operator () (int i) { cout<
int main() {
int a[] = {
1,
3,
4,
5};
vector<int> vc(a, a+
sizeof(a)/
sizeof(
int)); for_each(vc.begin(), vc.end(), Play()); }
输出是
#include
#include
#include
#include
using namespace std; struct Play { Play() { cout<<"new a Play"<
const Play&) {
cout<<
"new a copy Play"<
void
operator () (
int i) {
cout<
cout<<
"dispose a Play"<
int main() {
int a[] = {
1,
3,
4,
5};
vector<int> vc(a, a+
sizeof(a)/
sizeof(
int)); for_each(vc.begin(), vc.end(), Play());
cout<<
"See something"<
此时输出是:
2、传入参数
可以通过构造函数的技巧传入参数
#include
#include
#include
#include
using namespace std; struct Play { const char* str; Play(const char* s):str(s) {} void operator () (int i) { cout<
int main() {
int a[] = {
1,
3,
4,
5};
vector<int> vc(a, a+
sizeof(a)/
sizeof(
int)); for_each(vc.begin(), vc.end(), Play(
"Element:")); }
Member function 与 for_each 搭配
1、不传入参数
通过mem_fun_ref() 这个funtion adapater 将 member funtion 转成 function object。
#include
#include
#include
#include
using namespace std; class Door { public: void open() const { cout<<"open door horizontally"<
class DoorController {
protected:
vector
_doorVec;
public:
void addDoor(Door door) { _doorVec.push_back(door); }
void openDoor()
const { for_each(_doorVec.begin(), _doorVec.end(), mem_fun_ref(&Door::open)); } };
int main() { DoorController dc; dc.addDoor(Door()); dc.addDoor(Door()); dc.openDoor(); }
输出:
值得注意的是,mem_fun_ref() 用在 object 的 member function。若要搭配多态,vector必须放pointer,也就是得使用object pointer的member function,此时得使用mem_fun()将member function转成function object。
2、传入参数
要使用 bind2nd
#include
#include
#include
#include
using namespace std; class AbstractDoor { public: virtual void open(const char* str) const = 0; //定义纯虚函数 virtual ~AbstractDoor() {} }; class HorizontalDoor: public AbstractDoor { public: void open(const char* str) const { cout<
"open door horizontally"<
class VerticalDoor:
public AbstractDoor {
public:
void open(
const
char* str)
const {
cout<
"open door vertically"<
class DoorController {
protected:
vector
_doorVec;
public:
void addDoor(AbstractDoor* door) { _doorVec.push_back(door); }
void openDoor()
const { for_each(_doorVec.begin(), _doorVec.end(), bind2nd(mem_fun(&AbstractDoor::open),
"Jhon ")); } ~DoorController() { for_each(_doorVec.begin(), _doorVec.end(), [](AbstractDoor* p) {
delete p; p =
nullptr; }); } };
int main() { DoorController dc; dc.addDoor(
new HorizontalDoor()); dc.addDoor(
new VerticalDoor()); dc.openDoor(); }
引用一句很重要的用法:
mem_fun_ref的作用和用法跟mem_fun一样,唯一的不同就是:当容器中存放的是对象实体的时候用mem_fun_ref,当容器中存放的是对象的指针的时候用mem_fun。
Generics与for_each()搭配
1. Funtion template
1.1 不传入参数
#include
#include
#include
#include
using namespace std; template<typename T> void play(T elem) { cout<
int main() {
int a[] = {
1,
3,
4,
5};
vector<int> vc(a, a+
sizeof(a)/
sizeof(
int)); for_each(vc.begin(), vc.end(), play<
int>); }
1.2 传入参数
#include
#include
#include
#include
using namespace std; template<typename T, char str> void play(T elem) { cout<
int main() {
int a[] = {
1,
3,
4,
5};
vector<int> vc(a, a+
sizeof(a)/
sizeof(
int)); for_each(vc.begin(), vc.end(), play<
int,
'a'>); }
这里无法传入字串或者别的指针的类型。
2. class template
2.1不传入参数
#include
#include
#include
#include
using namespace std; template<typename T> class Play/*:public unary_function
*/
//我不懂为什么原文需要这个? { public: void operator() (T elem) { cout<
int main() {
int a[] = {
1,
3,
4,
5};
vector<int> vc(a, a+
sizeof(a)/
sizeof(
int)); for_each(vc.begin(), vc.end(), Play<
int>()); }
2.2 传入参数
#include
#include
#include
#include
using namespace std; template<typename T, typename V> class Play/*:public unary_function
*/
//我不懂为什么原文需要这个? { V _str; public: Play(V str):_str(str) {} void operator() (T elem) { cout<<_str<
int main() {
int a[] = {
1,
3,
4,
5};
vector<int> vc(a, a+
sizeof(a)/
sizeof(
int)); for_each(vc.begin(), vc.end(), Play<
int,
const
char*>(
"Element ")); }
END
发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/199421.html原文链接:https://javaforall.net
