变换的签名是:
OutputIterator transform (InputIterator first1, InputIterator last1,
OutputIterator result, UnaryOperation op);
我想创建一个通用标记替换下面的functor,msg_parser,所以我可以使用任何容器(下面的例子中使用的字符串)并传递容器的开始和结束进行转换。这个想法。
但我无法将其编译。
这是我的代码。任何帮助将不胜感激。
#include <iostream>
#include <iterator>
#include <string>
#include <map>
#include <algorithm>
class msg_parser {
public:
msg_parser(const std::map<std::string, std::string>& mapping, const char token = '$')
: map_(mapping), token_(token) {}
// I can use a generic istream type interface to handle the parsing.
std::ostream_iterator operator() (std::istream_iterator in) {
//body will go through input and when get to end of input return output
}
private:
const char token_;
const std::map<std::string, std::string>& map_;
};
int main(int argc, char* argv[]) {
std::map<std::string, std::string> mapping;
mapping["author"] = "Winston Churchill";
std::string str_test("I am $(author)");
std::string str_out;
std::transform(str_test.begin(), str_test.end(), str_out.begin(), msg_parser(mapping));
return 0;
}
答案 0 :(得分:3)
由于std::string
是char
s的集合,std::transform
将完全重复字符 distance(first1, last1)
次,所以在您的情况下它&# 39;不可能改变字符串的大小。您可以将"$(author)"
转换为另一个字符串完全相同的,但我想这不是您想要的。
您可能希望迭代流迭代器而不是chars:
std::stringstream istrstr(str_test);
std::stringstream ostrstr;
std::transform(std::istream_iterator<std::string>(istrstr),
std::istream_iterator<std::string>(),
std::ostream_iterator<std::string>(ostrstr, " "), // note the delimiter
msg_parser(mapping));
std::cout << ostrstr.str() << std::endl;
顺便说一句,你的UnaryOperation
适用于迭代类型,而不适用于迭代器,所以operator()
应该是:
std::string operator() (std::string in) { // ...
答案 1 :(得分:1)
您应该在this等参考中阅读std::transform
的文档和示例。
您会注意到操作应采用输入容器的元素并为输出容器生成元素。由于您的容器是字符串且元素是字符,因此签名应为char operator()(char)
。在这种情况下,容器迭代器是错误的。无论如何,std::string
的迭代器都是char*
s,所以你的std::ostream_iterator
完全没有意义。
话虽如此,你会发现变换适用于单个字符,如果你将它应用于你的字符串,而不是整个“author”子字符串。您尝试做的最好是使用C ++ 11的std::regex
正则表达式库,而不是std::transform