首页 > 解决方案 > 复制一套以逗号分隔的 std::string?

问题描述

假设我有一个通用的ints 列表。它可以是std::set

std::set<int> myInts;
myInts.insert(1);
myInts.insert(2);
myInts.insert(3);

我想将它们转换为std::string值之间的逗号(而不是在最后一个值之后!)。

我在这里搜索,有很多不同的解决方案。

例如,一个简单的单线:

copy(v.begin(), v.end(), ostream_iterator<string>(cout, ","));

这有效,但是

  1. 它在末尾添加了一个额外的“,”
  2. 因为我需要字符串作为输出,所以我必须使用一个中间额外的字符串流,这会导致不必要的性能开销。

我也可以使用基本的 foreach,我可以纠正最后一个逗号问题,还可以将这些整数转换为字符串,并将它们连接到输出字符串,但感觉不是最好(最快)的方法。

Boost 不可用,编译器是支持 C++14 的 CLANG。

set<int>将其转换为 CSV 字符串的最佳方式(性能方面)是什么?ostream_iterator(我可以测量方法和方法之间的执行时间差foreach,但这里的问题是是否还有其他东西可以满足我的所有愿望?

标签: c++csv

解决方案


最简单的方法可能是这样的:

std::set<int> set = {1, 2, 3, 4};
std::string s = std::to_string(*set.begin());

std::for_each(std::next(set.begin()), set.end(), [&s] (int val) {
    s.append(", ").append(std::to_string(val));
});

如果您担心性能,则需要预先分配足够大的缓冲区并改用 to_chars 或 sprintf。我不会认为这种情况对优化很重要,因为转换为 csv 是一种罕见的操作。

std::set<int> set = {1, 2, 3, 4};

//remember to check for errors when using sprintf, I am not.
char buf[1024];
int idx = std::sprintf(buf, "%d", *set.begin());

std::for_each(std::next(set.begin()), set.end(), [&buf, &idx] (int val) {
    idx += std::sprintf(buf + idx, ", %d", val);
});

std::string s(buf);

推荐阅读