相关疑难解决方法(0)

让std :: ifstream处理LF,CR和CRLF?

具体来说我很感兴趣istream& getline ( istream& is, string& str );.是否有ifstream构造函数的选项告诉它将所有换行编码转换为引擎盖下的'\n'?我希望能够打电话getline并优雅地处理所有行结尾.

更新:为了澄清,我希望能够编写几乎可以在任何地方编译的代码,并且几乎可以从任何地方获取输入.包括'\ r'没有'\n'的稀有文件.最大限度地减少软件用户的不便.

解决这个问题很容易,但我仍然对标准中正确处理所有文本文件格式的方式感到好奇.

getline读取一个完整的行,直到'\n',成为一个字符串.'\n'从流中消耗,但getline不包含在字符串中.到目前为止这很好,但是在'\n'之前可能会有一个'\ r'被包含在字符串中.

三种类型的行结尾的文本文件中看到:"\n"是Unix机器上的常规结尾,"\ r"是在旧的Mac操作系统使用,Windows使用一对(我认为),"\ r"跟随'\n'.

问题是getline在字符串末尾留下'\ r'.

ifstream f("a_text_file_of_unknown_origin");
string line;
getline(f, line);
if(!f.fail()) { // a non-empty line was read
   // BUT, there might be an '\r' at the end now.
}
Run Code Online (Sandbox Code Playgroud)

编辑感谢Neil指出这f.good()不是我想要的.!f.fail()是我想要的.

我可以自己手动删除它(请参阅此问题的编辑),这对于Windows文本文件很容易.但是我担心有人会输入一个只包含'\ r'的文件.在这种情况下,我认为getline将消耗整个文件,认为它是一行!

..那甚至不考虑Unicode :-)

..也许Boost有一种很好的方式从任何文本文件类型一次消耗一行?

编辑我正在使用它来处理Windows文件,但我仍然觉得我不应该这样做!这不会为'\ r'专用文件分叉.

if(!line.empty() && *line.rbegin() == '\r') {
    line.erase( line.length()-1, 1);
}
Run Code Online (Sandbox Code Playgroud)

c++ newline ifstream

79
推荐指数
3
解决办法
5万
查看次数

在C++ 11中使用正则表达式lookbehinds

为什么我不能在C++ 11中使用lookbehinds?Lookahead工作得很好.

std::regex e("(?<=a)b");
Run Code Online (Sandbox Code Playgroud)

这将抛出以下异常:

The expression contained mismatched ( and ).
Run Code Online (Sandbox Code Playgroud)

这不会抛出任何异常:

std::regex e("a(?=b)");
Run Code Online (Sandbox Code Playgroud)

我错过了什么?

c++ regex c++11

11
推荐指数
1
解决办法
4458
查看次数

Visual Studio regex_iterator Bug?

我在Visual Studio 2013上,我看到了我认为的错误,我希望有人可以证实?

string foo{ "A\nB\rC\n\r" };
vector<string> bar;

for (sregex_iterator i(foo.cbegin(), foo.cend(), regex("(.*)[\n\r]{1,2}")); i != sregex_iterator(); ++i){
    bar.push_back(i->operator[](1).str());
}
Run Code Online (Sandbox Code Playgroud)

此代码命中Visual Studio regex库中的Debug Assertion:

regex_iterator

如果我定义regex外部for-loop就可以了:

string foo{ "A\nB\rC\n\r" };
vector<string> bar;
regex bug("(.*)[\n\r]{1,2}");

for (sregex_iterator i(foo.cbegin(), foo.cend(), bug); i != sregex_iterator(); ++i){
    bar.push_back(i->operator[](1).str());
}
Run Code Online (Sandbox Code Playgroud)

或者,这可以在转换中正常工作,如此问题所示:

string foo{ "A\nB\rC\n\r" };
vector<string> bar;

// This puts {"A", "B", "C"} into bar
transform(sregex_iterator(foo.cbegin(), foo.cend(), regex("(.*)[\n\r]{1,2}")), sregex_iterator(), back_inserter(bar), [](const smatch& i){ return i[1].str(); });
Run Code Online (Sandbox Code Playgroud)

有人可以证实这是一个错误吗?

c++ regex assertion c++11 visual-studio-2013

8
推荐指数
1
解决办法
514
查看次数

标签 统计

c++ ×3

c++11 ×2

regex ×2

assertion ×1

ifstream ×1

newline ×1

visual-studio-2013 ×1