使用std :: transform将字符串转换为全部大写字母

时间:2011-05-11 10:58:15

标签: c++ stl

我正在使用变换算法和std :: toupper来实现这一点,但这可以在一行中完成吗?

transform(s.begin(), s.end(), ostream_iterator<string>(cout, "\n"),std::toupper);

我得到错误,所以我必须为此创建一个函数并使用transform调用它或者我可以使用一些适配器吗?

2 个答案:

答案 0 :(得分:9)

使用ostream_iterator<char>代替ostream_iterator<string>

transform(s.begin(),s.end(),ostream_iterator<char>(cout,"\n"),std::toupper);

std::transform转换每个字符并将其传递给输出迭代器。这就是为什么输出迭代器的type参数应该是char而不是std::string

顺便说一句,每个角色都会打印在换行符上。那是你要的吗?如果没有,请不要通过"\n"

-

注意:您可能必须使用::toupper代替std::toupper

见这些

答案 1 :(得分:4)

首先,如果你想输出char s(以及所有char s),你将会 需要使用ostreambuf_iterator<char>,而不是 ostream_iterator<string>。而且ostreambuf_iterator<char>表达了 比ostream_iterator<char>更能满足您的需求;你是 直接输出char,而不是格式化任何内容。 (ostream_iterator使用格式化的<<运算符。)

其次,请注意并非总是有一对一的翻译 从低到高(例如'ß'映射到中的两个字符序列"SS" 大写),所以std::transform不能真正用于完成这项工作 正确。 (当然,它不处理像你这样的多字节编码 UTF-8正确。)除了最简单的用途,你需要一些东西 更复杂。但即使是最简单的情况:

std::toupper被重载:其中一个重载是模板,其中 有两个参数,另一个是一个单一的函数 int;这两个都不会直接在这里工作,transform也是如此 模板也意味着重载决议和模板类型 扣除即使他们这样做也行不通。所以基本上,你必须添加 一些东西。如果您可以使用2参数模板函数 添加足够的限定符并使用boost::bind或类似绑定的东西 第二个论点,但它几乎和写一个简单的文本一样多 toupper功能性论证你的自我。你不能使用单身 参数形式(如果包含,可以明确访问) <ctype.h>并使用::toupper)因为它具有未定义的行为 当你调用它时,你使用char作为参数:你必须转换 首先是charunsigned char(当然,除非是普通char 在你正在使用的实现中没有签名 - 总而言之 您的代码将被移植到的实现。)