std::transform
std::transform
是 C++ 标准库 <algorithm>
中的一个重要算法,用于对容器(如 std::string
、std::vector
等)中的元素进行转换操作。它有两种主要形式:
1. 基本语法
(1) 一元操作(单范围转换)
OutputIt transform(InputIt first1, InputIt last1, OutputIt d_first, UnaryOperation unary_op);
-
功能:对输入范围
[first1, last1)
的每个元素应用unary_op
,并将结果存储到d_first
开始的输出位置。 -
参数:
-
first1
,last1
:输入范围的起始和结束迭代器。 -
d_first
:输出位置的起始迭代器(可以是输入容器的起始位置,实现原地修改)。 -
unary_op
:一元操作函数(如::tolower
、::toupper
或自定义 lambda)。
-
-
返回值:返回输出范围的结束迭代器(
d_first + (last1 - first1)
)。
(2) 二元操作(双范围合并)
OutputIt transform(InputIt1 first1, InputIt1 last1, InputIt2 first2, OutputIt d_first, BinaryOperation binary_op);
-
功能:对两个输入范围
[first1, last1)
和[first2, first2 + (last1 - first1))
的对应元素应用binary_op
,结果存储到d_first
。 -
参数:
-
first2
:第二个输入范围的起始迭代器(长度需与第一个范围匹配)。 -
binary_op
:二元操作函数(如std::plus<>()
或自定义 lambda)。
-
-
返回值:同上。
2. 常见用法示例
(1) 字符串大小写转换
#include <algorithm>
#include <cctype>
#include <string>std::string s = "Hello, World!";// 转换为小写(原地修改)
std::transform(s.begin(), s.end(), s.begin(), ::tolower);
// s = "hello, world!"// 转换为大写(输出到新字符串)
std::string upper;
upper.resize(s.size());
std::transform(s.begin(), s.end(), upper.begin(), ::toupper);
// upper = "HELLO, WORLD!"
(2) 数学运算(如对 vector 元素平方)
#include <vector>std::vector<int> nums = {1, 2, 3, 4};// 原地平方
std::transform(nums.begin(), nums.end(), nums.begin(), [](int x) { return x * x; });
// nums = {1, 4, 9, 16}
(3) 合并两个容器(如向量加法)
std::vector<int> a = {1, 2, 3};
std::vector<int> b = {4, 5, 6};
std::vector<int> result(3);// a + b -> result
std::transform(a.begin(), a.end(), b.begin(), result.begin(), std::plus<int>());
// result = {5, 7, 9}
(4) 自定义转换(如提取字符串长度)
std::vector<std::string> names = {"Alice", "Bob", "Charlie"};
std::vector<size_t> lengths(names.size());std::transform(names.begin(), names.end(), lengths.begin(),[](const std::string& s) { return s.size(); });
// lengths = {5, 3, 7}
3. 适用场景:
-
元素级转换(如大小写、数学运算)。
-
合并两个容器(如向量加法)。
-
提取或映射数据(如字符串→长度)。
s.begin()与begin(s)
主要区别
特性 | s.begin() (成员函数) | begin(s) (非成员函数) |
---|---|---|
调用方式 | s.begin() | begin(s) |
适用对象 | 标准库容器、自定义容器 | 标准库容器、C 数组、支持 ADL 的类型 |
C 数组支持 | ❌ 不支持 | ✅ 支持 |
泛型编程 | 可能受限(依赖成员函数) | 更通用(支持非成员函数和 ADL) |
- 在泛型代码中使用
begin(s)
(更灵活)。 - 在明确容器类型的代码中,两者均可,
s.begin()
更直观。
例如:
std::string s = "Hello";
std::vector<int> v = {1, 2, 3};
int arr[] = {4, 5, 6};// 统一使用 begin(s) 风格(推荐)
auto s_it = begin(s); // OK
auto v_it = begin(v); // OK
auto arr_it = begin(arr); // OK// 也可以混用
auto s_it2 = s.begin(); // OK
auto v_it2 = v.begin(); // OK
// auto arr_it2 = arr.begin(); // 错误!