C++ STL算法总结

大多重载的算法都同时有两个版本的:算法

  • 用"=="判断元素相等,或者用"x<y,y<x"比较大小判断相等
  • 多出一个类型参数"Pred"和函数形参"Pred op",经过判断表达式op(x,y)的返回值来判断x==y或者x<y。 好比有两个版本的min_element:
iterator min_element(iterator first, iterator last);
iterator min_element(iterator first, iterator last,Pred op);
复制代码

STL中的算法大体有如下7种:bash

须要说明的是,算法名字并不表明实际意义,能够用本身的想象力作算法名字以外的事情;同时有些很是用算法并未列出dom

1.不变序列算法

该类算法不修改算法所做用的容器或对象函数

适用于顺序容器和关联容器性能

时间复杂度都是O(n)测试

经常使用算法:ui

名称 说明(代码为函数模板,InIt表明迭代器,简单的不说明)
find InIt find(InIt first, InIt last, const T& val);
count size_t count(InIt first, InIt last, const T& val);
min
max
min_element FwdIt min_element(FwdIt first, FwdIt last);
max_element FwdIt max_element(FwdIt first, FwdIt last);
search 查找另外一区间第一次出现的位置
find_first_of
find_end
equal 判断两区间是否相等
for_each Fun for_each(InIt first, InIt last, Fun f);

2.变值算法

会修改源区间或目标区间元素的值spa

值被修改的那个区间不能够是关联容器(关联容器会涉及到从新排序)code

经常使用算法:orm

名称 说明(Init输入迭代器,OutIt输出迭代器)
for_each
copy OutIt copy(InIt first, InIt last, OutIt x);
copy_backward
transform OutIt transform(InIt first, InIt last, OutIt x, Unop uop);
swap_ranges
fill
fill_n
generate
generate_n
replace
replace_if
replace_copy
replace_copy_if

3.删除算法

删除一个容器中的某些元素

删除算法不该做用于关联容器(关联容器会涉及到元素排序)

算法复杂度都是o(n)

删除并不会使元素减小

* 将全部应该被删除的元素看作空位子
* 用留下的元素从后往前移, 依次去填空位子
* 空位置填满后,剩下的位置由刚开始的所在位置元素填(即剩下的位置不变)
复制代码
名称 说明
remove 删除区间中等于某个值的元素
unique 删除区间中连续相等的元素, 只留下一个(可自定义比较器)
remove_if
remove_copy
remove_copy_if
unique_copy

4.变序算法

变序算法改变容器中元素的顺序,可是不改变元素的值

变序算法不适用于关联容器

算法复杂度都是O(n)的

名称 说明(FwdIt迭代器)
reverse 颠倒区间的先后次序
rotate 将区间进行循环左移
next_permutation 将区间改成下一个排列(可自定义比较器)
prev_permutation 将区间改成上一个排列(可自定义比较器)
random_shuffle 随机打乱区间内元素的顺序
stable_patition 把区间内知足某个条件的元素移到前面,不知足该条件的移到后面,而对这两部分元素, 分别保持它们原来的前后次序不变
partition 把区间内知足某个条件的元素移到前面,不知足该条件的移到后面
rotate_copy 将区间以首尾相接的形式进行旋转后的结果拷贝到另外一个区间,源区间不变
reverse_copy 把一个区间颠倒后的结果拷贝到另外一个区间,源区间不变

5.排序算法

排序算法须要随机访问迭代器的支持

不适用于关联容器和list

比前面的变序算法复杂度更高, 通常是O(nlog(n))

名称 说明(RanIt迭代器)
sort void sort(RanIt first, RanIt last, Pred pr)
stable_sort
partial_sort
partial_sort_copy
nth_element
make_heap
push_heap
pop_heap
sort_heap

sort 其实是快速排序, 时间复杂度 O(n*log(n))

  • 平均性能最优
  • 可是最坏的状况下, 性能可能很是差

若是要保证 “最坏状况下” 的性能, 那么可使用stable_sort

  • stable_sort 其实是归并排序, 特色是能保持相等元素之间的前后次序
  • 在有足够存储空间的状况下, 复杂度为 n * log(n), 不然复杂度为n * log(n) * log(n)
  • stable_sort 用法和 sort相同。

排序算法要求随机存取迭代器的支持, 因此list不能使用排序算法, 要使用list自带的sort成员函数list::sort。

6.有序区间算法

要求所操做的区间是已经从小到大排好序的

须要随机访问迭代器的支持

有序区间算法不能用于关联容器和list

名称 说明(前6个很经常使用)
binary_search 判断区间中是否包含某个元素(折半查找)
includes 判断是否一个区间中的每一个元素,都在另外一个区间中
lower_bound 查找最后一个不小于某值的元素的位置
upper_bound 查找第一个大于某值的元素的位置
equal_range 同时获取lower_bound和upper_bound
merge 合并两个有序区间到第三个区间
set_union 将两个有序区间的并拷贝到第三个区间
set_intersection 将两个有序区间的交拷贝到第三个区间
set_difference 将两个有序区间的差拷贝到第三个区间
set_symmetric_difference 将两个有序区间的对称差拷贝到第三个区间
inplace_merge 将两个连续的有序区间原地合并为一个有序区间

bitset

bitset一个实际上不属于STL算法,可是会很经常使用。

template<size_t N>
class bitset{
    ...
}
bitset<40>bst; #bst是一个由40位组成的对象,用bitset的函数能够方便地访问任何一位
复制代码

bitset的成员函数:

bitset<N>& operator&=(const bitset<N>& rhs);
bitset<N>& operator|=(const bitset<N>& rhs);
bitset<N>& operator^=(const bitset<N>& rhs);
bitset<N>& operator<<=(size_t num);
bitset<N>& operator>>=(size_t num);
bitset<N>& set(); //所有设成1
bitset<N>& set(size_t pos, bool val = true); //设置某位
bitset<N>& reset(); //所有设成0
bitset<N>& reset(size_t pos); //某位设成0
bitset<N>& flip(); //所有翻转
bitset<N>& flip(size_t pos); //翻转某位 
reference operator[](size_t pos); //返回对某位的引用
bool operator[](size_t pos) const; //判断某位是否为1
reference at(size_t pos);
bool at(size_t pos) const;
unsigned long to_ulong() const; //转换成整数
string to_string() const; //转换成字符串
size_t count() const; //计算1的个数
size_t size() const;
bool operator==(const bitset<N>& rhs) const;
bool operator!=(const bitset<N>& rhs) const; 
bool test(size_t pos) const; //测试某位是否为 1
bool any() const; //是否有某位为1
bool none() const; //是否所有为0
bitset<N> operator<<(size_t pos) const;
bitset<N> operator>>(size_t pos) const;
bitset<N> operator~();
static const size_t bitset_size = N;
#注意: 第0位在最右边
复制代码

总结起来呢,就是实现容器或对象元素的查删改比较排序

相关文章
相关标签/搜索