2015-10-13 59 views
1

我有以下的功能,即写入vector到CSV文件:删除尾随逗号使用复制和ostream_iterator矢量书面

#include <math.h> 
#include <vector> 
#include <string> 
#include <fstream> 
#include <iostream> 
#include <iterator> 
using namespace std; 

bool save_vector(vector<double>* pdata, size_t length, 
       const string& file_path) 
{ 
    ofstream os(file_path.c_str(), ios::binary | ios::out); 
    if (!os.is_open()) 
    { 
     cout << "Failure!" << endl; 
     return false; 
    } 
    os.precision(11); 
    copy(pdata->begin(), pdata->end(), ostream_iterator<double>(os, ",")); 
    os.close(); 
    return true; 
} 

然而,CSV文件的结尾是这样的:

1.2000414752e-08,1.1040914566e-08,1.0158131779e-08,9.3459324063e-09, 

也就是说,一个尾随逗号被写入文件。当我尝试使用其他软件程序加载文件时,这会导致错误。

什么是最简单,最有效的方法来摆脱(理想情况下,永远不会写)这个尾随逗号?

+0

您的问题将很快得到解决:http://en.cppreference.com/w/cpp/experimental/ostream_joiner – vsoftco

回答

3

正如您所观察到的,通过std::copy进行复制并不能解决问题,只会输出一个,。有一个提案可能会在未来的C++ 17标准中做到:ostream_joiner,这将完全符合您的期望。

但是,现在可用的快速解决方案是手动完成。

for(auto it = std::begin(*pdata); it != std::end(*pdata); ++it) 
{ 
    if (it != std::begin(*pdata)) 
     std::cout << ","; 
    std::cout << *it; 
} 
+0

我现在正在使用'-std = C++ 11'作为编译器选项。它看起来不会为我工作(关于获得'实验')。我应该使用什么?或者也许我需要安装'实验性的'? – dbliss

+0

它似乎还没有包含在gcc中,我无法用gcc5.2编译。 – vsoftco

+0

我一直在使用'C++'版本4.8.4和'g ++'版本4.8.4(可能会也可能不是同一件事),但没有运气。 – dbliss

0

我是忽略处理的第一要素特种印刷的逗号:

if (!pdata->empty()) { 
    os << pdata->front(); 
    std::for_each(std::next(pdata->begin()), pdata->end(), 
        [&os](auto&& v){ os << ", " << v; }); 
} 

显然,这个代码进入打印打印范围适配器的功能。

+0

我不明白究竟是如何工作的。你不应该去'end() - 1'元素吗?但是如果你把最后一个元素看作是特殊的,那么你会遇到一些问题。 'std :: forward_list',它只有ForwardIterable。 – vsoftco

+0

@vsoftco:是的,有一个-1失踪。 ...是的,它不适用于'std :: forward_list',这不是问题所在(使用'-1'实际上也不能用于'std :: list',但可以使用'std :: prev()')修复。 –