泛型算法定义:
泛型因为他们可以用于不同类型的元素和多种容器类型(不仅包括标准库类型,还包括内置的数组类型),以及我们将看到的,还能用与其他类型的序列。
算法因为他们实现了一些经典算法的公共接口。
本章所介绍的几个函数
1、find:定义在头文件algorithm中,有三个参数,其中前两个至少为输入迭代器(指针),第三个参数是一个值。他返回第一个等于给定值元素的迭代器。从第一个参数开始寻找,如果没有找到,则返回其第二个参数。也就是说第二个参数来表示搜素失败。
eg: auto result = find( vec.begin(), vec.end(), 0);
2、find_if:定义在头文件algorithm中,调用返回一个迭代器,查找一个满足条件的元素,若不存在,返回第二个参数。
eg: auto result = find_if( vec.begin(), vec.end(), [sz](const string &a){return a.size() >= sz;});
此处涉及到lambda表达式。
3、count:定义在头文件algorithm中,类似于find,接受一对迭代器和一个值作为参数。返回给定制在序列中出现的次数。
eg: cout << count( vec.begin(), vec.end(), 0);
4、accumulate:定义在头文件numeric中。只读算法,接受三个参数,前两个表示范围与find类似,第三个参数是和的初值。例中将sum设置为vec中元素的和。
eg:int sum = accumulate( vec.begin(), vec.end(), 0);
5、equal:定义在头文件algorithm中,只读算法,接受三个迭代器,前两个表示第一个序列的元素范围,第三个表示第二个序列的首元素。他将第一个序列中的每个元素与第二个序列中的对应元素进行比较。如果所有元素都对应相等返回true,否则返回false。(容器类型以及元素类型都不必一样,但第二个序列至少与第一个序列一样长)
eg:equal(roster1.cbegin(), roster1.cend(), roster2.cbegin());
6、fill:定义在头文件algorithm中,接受三个参数,前两个为一对迭代器,表示范围,第三个为一个值,fill将这个值赋予输入序列中的每个元素。
eg:fill(vec.begin(), vec.end(), 0);
7、fill_n:定义在头文件algorithm中,接受一个单迭代器,一个计数值和一个值。它将给定值赋予迭代器指向的元素开始的指定个元素。
eg:fiil_n(vec.begin(), vec.size(), 0);
8、copy:定义在头文件algorithm中,接受三个迭代器,前两个表示一个输入范围,第三个表示目的序列的起始位置。该算法是向目的位置迭代器指向的输出序列中的元素写入数据的算法。他将输入范围内的元素拷贝到目的序列中。(传递给copy的目的序列至少要包含于输入序列一样多的元素,必须初始化或者使用back_inserter插入)。返回的是其目的位置迭代器(递增后)的值。
eg:auto ret = copy(vec.begin(), vec.end(), back_inserter(ivec));
9、replace:定义在头文件algorithm中,接受四个参数,前两个是迭代器,表示输入序列,后两个一个是要搜索的值,另一个是新值。他将所有等于第一个值的元素替换成为第二个值。
eg:replace(ilst.begin(), ilst.end(), 0, 42);
10、replace_copy:在replace基础上,如果我们想保持原序列不变,可以调用replace_copy。此算法接受额外第三个迭代器参数,指出调整后序列的保存位置。下例中调用后,ilst并未改变,ivec包含ilst的一份拷贝,不过原来在ilst中值为0的元素在ivec中变为42。
eg:replace_copy(ilst.begin(), back_inserter(ivec), 0, 42);
11、sort:定义在头文件algorithm中,sort算法接受两个迭代器,表示要排序的元素范围。
eg:sort(words.begin(), words.end());
12、stable_sort:定义在头文件algorithm中,一种稳定排序算法维持相等元素的原有顺序。可以保持登场元素间的字典序。
eg:stable_sort(words.begin(), words.end(), isShoter);
此处isShoter是一个二元谓词。
13、unique:算法重排输入序列,将相邻的重复”消除“,并返回一个指向不重复值范围末尾的迭代器。实际并未删除,末尾还存在一些未知元素,需要使用erase删除。接受一对迭代器表示范围。
eg:auto end_unique = unique(words.begin(), words.end());
14、for_each:此算法接受一个可调用对象,并对输入序列中的每个元素调用此对象。
eg:for_each(wc, words.end(), [](const string &s) {cout << s << " ";});
15、transform:定义在头文件algorithm中,接受三个迭代器和一个可调用对象。前两个迭代器表示目的位置,第三个迭代器表示目的位置。算法对输入序列开始位置的迭代器调用可调用对象,并将结果写到目的位置。目的位置迭代器与表示输入序列开始位置的迭代器可以是相同的。当输入迭代器和目的迭代器相同时,transform将输入序列中每个元素替换为可调用对象操作该元素得到的结果。
eg:transform(vi.begin(), vi.end(), vi.begin(), [](int i){return i < 0 ? -i : i;});