如何重用字符串流

问题描述 投票:0回答:7

这些帖子没有回答我:

重置字符串流

如何清除字符串流变量?

std::ifstream file( szFIleName_p );
if( !file ) return false;

// create a string stream for parsing

std::stringstream szBuffer;

std::string szLine;     // current line
std::string szKeyWord;  // first word on the line identifying what data it contains

while( !file.eof()){

    // read line by line

    std::getline(file, szLine);

    // ignore empty lines

    if(szLine == "") continue;

    szBuffer.str("");
    szBuffer.str(szLine);
    szBuffer>>szKeyWord;

szKeyword
将始终包含第一个单词,
szBuffer
不会被重置。我在任何地方都找不到关于如何使用 stringstream 的明确示例。

回答后的新代码:

...
szBuffer.str(szLine);
szBuffer.clear();
szBuffer>>szKeyWord;
...

好的,这就是我的最终版本:

std::string szLine;     // current line
std::string szKeyWord;  // first word on the line identifying what data it contains

// read line by line

while( std::getline(file, szLine) ){

    // ignore empty lines

    if(szLine == "") continue;

    // create a string stream for parsing

    std::istringstream szBuffer(szLine);
    szBuffer>>szKeyWord;
c++ file parsing text stringstream
7个回答
36
投票

您在拨打

clear()
后没有
str("")
直播。再看一下这个答案,它也解释了为什么你应该使用
str(std::string())
重置。在您的情况下,您还可以仅使用
str(szLine)
重置内容。

如果您不调用

clear()
,流的标志(如
eof
)将不会被重置,从而导致令人惊讶的行为;)


10
投票

这取决于你用它做什么。通常更容易 创建一个新的

istringstream
ostringstream
。要“重置”流, 你必须清除它的缓冲区,清除任何错误标志,重置任何 格式化标志,加上精度和填充,用 原始语言环境,并且不要忘记任何扩展格式信息 使用从
imbue
返回的值生成。总而言之,不可能 得到正确的。

当我这样做时,你的循环是错误的,并且可能会导致 最后一行被处理两次。

xalloc

仅具有可用意义 输入失败后(即使如此,也不是 100% 可靠)。 你想要的是:


file.eof()

(实际上,您可能想修剪该行的尾随空白
在测试空之前。)


3
投票

第一步:ss.clear();
  • 第二步:ss.str("");
  • 重用字符串流——彻底清除字符串流。


1
投票
std::string line; while ( std::getline( file, line ) ) { if ( !line.empty() ) { std::istringstream buffer( line ); // ... } }

istringstream
比重置相同的更容易。

但是,如果您确实想怨恨他们:

    使用
  • ostringstream

    重新发送流标志(以避免意外行为)。

    
    

  • 虽然您可以使用
  • clear ()

    更正

    stringstream
    的内容,但出于效率目的,我们可能更喜欢
    str ("")
    
    


0
投票
str(std::string())

, 然后只需

unique_ptr<stringstream>
即可重复使用它。
    


0
投票

reset(new stringstream(...))

代码:

par1=11 par2=22

goodbit 为零,表示其他位均未设置


0
投票
std::string line, strpar1, strpar2; int par1, par2; std::ifstream configfile("config.cfg"); std::getline(configfile, line); // first line to variable "line" std::istringstream sline(line); while (std::getline(sline, strpar1, '=')); par1 = std::stoi(strpar1); // par1 get 11 bool b = sline.eof(); // true std::getline(configfile, line); // second line to variable "line" sline.clear(); // sline.str(line); // reuse "sline" b = sline.good(); // true // goodbit is zero, indicating that none of the other bits is set. b = sine.fail(); // false b = sline.bad(); // false b = sline.eof(); // false while (std::getline(sline, strpar2, '=')); par2 = std::stoi(strpar2); // par2 get 22

,您需要首先重置标志并将内部

stringstream
ptr 设置为开头
stringbuf

这将在每次 
std::stringstream ss; ... ss.clear(); ss.seekp(0, std::ios_base::beg);

调用后打印正确的值。

注意,

str()

不会重置使用的格式标志,并且每个

clear()
调用都会复制出一个新字符串。因此,重用
str()
几乎没有时钟周期优势。对于使用特定于线程的应用程序
stringstream
,这种行为是浪费资源。
    

© www.soinside.com 2019 - 2024. All rights reserved.