把vector里面的数字都乘以2
#include <vector>
#include <algorithm>
#include <vector>
using namespace std;
int main()
{
vector<int> xs{ 1,2,3,4,5 };
transform(begin(xs), end(xs), begin(xs), [](int x) {return x * 2; });
return 0;
}
transform
的第三个参数也可以是别的容器的某个位置,如果你确保目标容器有足够的位置的话,transform
还能一边执行你的函数一边复制。
把vector的奇数复制到另一个vector
#include <vector>
#include <algorithm>
#include <vector>
#include <iterator>
using namespace std;
int main()
{
vector<int> xs{ 1,2,3,4,5 };
vector<int> ys;
copy_if(begin(xs), end(xs), back_inserter(ys), [](int x) {return x % 2 == 1; });
return 0;
}
copy_if
还有很多类似的办法,可以不要条件,还可以控制方向等等。
大家可能会注意到这里使用了back_inserter
函数。这是<iterator>
里面的一个函数,从一个容器返回一个特殊的迭代器,会在迭代器内容被修改的时候去调用容器的push_back
函数。上一页的transform
自然也可以配合它来使用。<iterator>
文件里面还有很多类似的迭代器,这样你就不需要在容器预先留好空间了(很多容器也无法预留,譬如说链表)。
把vector的所有奇数放在前面,偶数放在后面
#include <vector>
#include <algorithm>
using namespace std;
int main()
{
vector<int> xs{ 1,2,3,4,5 };
partition(begin(xs), end(xs), [](int x) {return x % 2 == 1; });
return 0;
}
partition
函数把所有 lambda 表达式返回true
的都放在了前面,然后它会返回给你一个 iterator,指向摆放好之后第一个false
的元素的位置。需要注意的是,尽管xs
一开始是有顺序的,但是partition
一下之后,顺序是不保证的。
把vector的所有字符串使用空格连接在一起
#include <vector>
#include <numeric>
#include <iostream>
#include <string>
using namespace std;
int main()
{
vector<string> xs{ "I","am","a","C++","programmer" };
cout <<
accumulate(
begin(xs),
end(xs),
string(),
[](const string& a, const string& b)
{
return a == "" ? b : a + " " + b;
}
)
<< "!" << endl;
return 0;
}
这个程序会输出I am a C++ programmer!
。别看accumulate
是从<numeric>
来的,但是既然是通用算法,就没有任何理由不能用在字符串上面。当然正常的用法是:
- 给0和加法求和(任何数字加上0没有变化)
- 给1和乘法求积(任何数字加上1没有变化)
这样的东西。我们给的 lambda 表达式自然也要符合这个规律。accumulate
的第三个参数是一个空字符串,然后我们使用 lambda 表达式保证了,任何字符串跟这个空字符串弄在一起不会变化。
文档参考
https://docs.microsoft.com/en-us/cpp/standard-library/algorithm?view=vs-2019
以上来自计蒜客 ?