寻找惯用的方式来连接对象的字符串表示
looking for idiomatic way to join string representations of objects
考虑到我们有这个:
示例代码A:
struct parameter
{
string name, value;
};
ostream& operator<<(ostream& out, const parameter& p)
{
return out << p.name << "=" << p.value;
}
示例代码B:
auto seq = {
parameter{ "language", "En" },
parameter{ "q", "search+term" }
};
vector<string> tmp;
transform(begin(seq), end(seq), std::back_inserter(tmp),
[](const auto& p) {
ostringstream out;
out << p;
return out.str();
});
auto result = boost::algorithm::join(tmp, "&");
有没有什么方法可以使 示例代码 B 更加地道?我试图在计算 result
.
时避免使用 tmp
最初我尝试直接在 seq
上调用 boost::algorithm::join
(这不起作用,因为连接仅适用于作为可连接元素的字符序列)。
我也可以使用单个 ostringstream
并完全放弃 boost::algorithm::join
(但这会附加一个额外的 &
),或者迭代元素的数量,并避免附加一个额外的明确地在末尾添加符号,或者定义我自己的 ostream 迭代器(但是 is a lot of code to write)。
谢谢
如果我理解正确,std::transform 缺少参数是 insert_iterator
到 tmp,最简单的方法(也是最快的!)如下所示:
std::ostringstream out;
for (auto&& item : seq)
out << item << "&";
std::string str = out.str();
if (str.size() > 0)
str.resize(str.size() - 1);
不需要使用丑陋的 lambda 语法进行复杂的转换,也不需要创建一个临时向量只是为了在其上调用 join 并重新分配。
对于更惯用的东西,您可以按以下方式使用 boost::adaptors::transformed
:
std::vector<parameter> seq = {{"language", "En"}, {"q", "search+term"}};
auto result = boost::algorithm::join(seq |
boost::adaptors::transformed([](parameter const &p){return p.name + "=" + p.value;}),
"&");
没有临时向量,没有昂贵的字符串流。
考虑到我们有这个:
示例代码A:
struct parameter
{
string name, value;
};
ostream& operator<<(ostream& out, const parameter& p)
{
return out << p.name << "=" << p.value;
}
示例代码B:
auto seq = {
parameter{ "language", "En" },
parameter{ "q", "search+term" }
};
vector<string> tmp;
transform(begin(seq), end(seq), std::back_inserter(tmp),
[](const auto& p) {
ostringstream out;
out << p;
return out.str();
});
auto result = boost::algorithm::join(tmp, "&");
有没有什么方法可以使 示例代码 B 更加地道?我试图在计算 result
.
tmp
最初我尝试直接在 seq
上调用 boost::algorithm::join
(这不起作用,因为连接仅适用于作为可连接元素的字符序列)。
我也可以使用单个 ostringstream
并完全放弃 boost::algorithm::join
(但这会附加一个额外的 &
),或者迭代元素的数量,并避免附加一个额外的明确地在末尾添加符号,或者定义我自己的 ostream 迭代器(但是 is a lot of code to write)。
谢谢
如果我理解正确,std::transform 缺少参数是 insert_iterator
到 tmp,最简单的方法(也是最快的!)如下所示:
std::ostringstream out;
for (auto&& item : seq)
out << item << "&";
std::string str = out.str();
if (str.size() > 0)
str.resize(str.size() - 1);
不需要使用丑陋的 lambda 语法进行复杂的转换,也不需要创建一个临时向量只是为了在其上调用 join 并重新分配。
对于更惯用的东西,您可以按以下方式使用 boost::adaptors::transformed
:
std::vector<parameter> seq = {{"language", "En"}, {"q", "search+term"}};
auto result = boost::algorithm::join(seq |
boost::adaptors::transformed([](parameter const &p){return p.name + "=" + p.value;}),
"&");
没有临时向量,没有昂贵的字符串流。