函数对象
很多STL算法都使用函数对象( for_each()、sort() )——也叫函数符(functor)。
包括函数名、指向函数的指针和重载了运算符'()'的类对象。
STL定义的函数符概念:
~生成器(generator):不用参数就可以调用的函数符;
~一元函数(unary function):用一个参数就可以调用的函数符(比如提供给for_each()的函数符);
~二元函数(binary function):用两个参数可以调用的函数符;
~谓词(predicate):返回bool值的一元函数;
list模板有一个将谓词作为参数的remove_if()成员,将谓词应用于区间中的每一个元素,若为真则删除。
~二元谓词(binary predictor):返回bool值的二元函数(比如提供给sort()的函数符)。
预定义的函数符
头文件functional定义了多个模板类函数:
自适应函数符和函数适配器:
自适应函数符携带了标识参数类型和返回类型的typedef成员(这些成员分别是result_type、first_arguement_type、second_arguement_type)。
函数符自适应的意义在于:函数适配器对象可以使用这些对象,并认为存在这些typedef成员。
STL使用binder1st和bind2nd类,自动将自适应二元函数转换为自适应一元函数。例:
binder1st(f2, val) f1;
f1(x); //相当于f2(val, x)
算法
STL包含很多处理容器的非成员函数:
sort()、copy()、find()、for_each()、replace()、random_shuffe()、set_union()、set_intersection()、set_difference()、transform()。
STL将算法库分为4种:
~非修改式序列操作;
~修改式序列操作;
~排序和相关操作;
~通用数字运算符(计算两个容器的内部乘积、计算相邻对相差等数组操作特性)。
前三组在头文件algorithm中描述;第四组在头文件numeric中描述。
copy()
copy(cast, cast+10, dice.begin()); //cast为数组名,dice为容器对象
要求dice有足够的空间,如果dice没有足够的空间,可以使用插入迭代器,将复制转为插入。
copy( cast, cast+10, insert_interator< vector<int> >(dice, dice.begin()) )
for_each()
一元函数遍历容器中的元素。
transform()
~使用接受一个参数的函数:transform( gr8.begin(), gr8.end(), out, sqrt ); //gr8为一种容器对象,out为使用cout输出流的输出迭代器对象,sqrt为一元函数符
~使用接受两个参数的函数:transform( gr8.begin(), gr8.end(), m8.begin, out, add); //gr8和m8为一种容器对象,out为使用cout输出流的输出迭代器对象,add为二元函数符
replace() / replace_copy() / replace_if()
~就地版本:replace(); //接收四个参数,迭代器区间、老值和新值
~复制版本:replace_copy(); //接收五个参数,迭代器区间,输出迭代器,老值和新值
~使用谓词的变体:replace_if(); //接收四个参数,迭代器区间,谓词,新值
random_shuffle()
接收两个参数(迭代器区间),随机排列该区间的元素。
sort()
~一种版本接收两个参数(迭代器区间),如果容器元素是用户定义的对象,要使用sort(),则必须定义operator<()函数。
~另一种版本接收三个参数,第三个参数为谓词。
next_permutation()
将区间内容自动转化成另一种排列方式,如果成功则返回true,如果区间已处于最后的序列中则返回false。
find()