很抱歉提出许多人可能认为已经被问过的问题。
我有一个很长的CSV数据文件(dat.csv),有5列。我有另一个带有1列的短CSV(filter.csv)文件。
现在,我只需要从dat.csv中提取列,其中column-1与filter.csv的column-1匹配。
我通常会使用sed/awk
在BASH中执行此操作。但是,由于某些其他原因,我需要在C ++文件中执行此操作。你能建议一种有效的方法吗?
示例数据:
data.csv
ID,Name,CountryCode,District,Population 3793,NewYork,USA,NewYork,8008278 3794,LosAngeles,USA,California,3694820 3795,Chicago,USA,Illinois,2896016 3796,Houston,USA,Texas,1953631 3797,Philadelphia,USA,Pennsylvania,1517550 3798,Phoenix,USA ,Arizona,1321045 3799,SanDiego,USA,California,1223400 3800,Dallas,USA,Texas,1188580 3801,SanAntonio,USA,Texas,1144646
filter.csv
3793 3797 3798
答案 0 :(得分:7)
这个.csv排序库可能会有所帮助:
http://www.partow.net/programming/dsvfilter/index.html
您可以将两个表的列合并为一个更大的表,然后在新表中查询匹配项(表A的第1列是表B的第1列)。或者也许该库具有比较表的功能。
答案 1 :(得分:1)
以下是一些提示:
您正在从中读取数据的流需要忽略逗号,因此它应该使用其语言环境中嵌入的std::ctype<char>
facet将逗号字符设置为空白。以下是修改分类表的示例:
struct ctype : std::ctype<char>
{
private:
static mask* get_table()
{
static std::vector<mask> v(classic_table(),
classic_table() + table_size);
v[','] &= ~space;
return &v[0];
}
public:
ctype() : std::ctype<char>(get_table()) { }
};
阅读第一个csv。文件行(意味着std::getline()
)。提取第一个单词并将其与第二个.csv文件中的提取进行比较。继续此操作,直到到达第一个文件的末尾:
int main()
{
std::ifstream in1("test1.csv");
std::ifstream in2("test2.csv");
typedef std::istream_iterator<std::string> It;
in1 >> comma_whitespace;
in2 >> comma_whitespace;
std::vector<std::string> in2_content(It(in2), It());
std::vector<std::string> matches;
while (std::getline(in1, line))
{
std::istringstream iss(line);
It beg(iss);
if (std::find(in2_content.begin(),
in2_content.end(), *beg) != in2_content.end())
{
matches.push_back(line);
}
}
}
// After the above, the vector matches should hold all the rows that
// have the same ID number as in the second csv file
comma_whitespace
是一个操纵器,可将区域设置更改为上面定义的自定义ctype
。
免责声明:我尚未测试此代码。