2

このようにストリングストリームすることは可能ですか? ifstream で読み込んで変換しようとしています。

string things = "10 11 12 -10";
int i1;
int i2;
int i3;
int i4;
stringstream into;
into << things;
into >> i1;
into >> i2;
into >> i3;
into >> i4;

私はそれが次のようになることを期待しています:

i1 = 10
i2 = 11
i3 = 12
i4 = -10

あれは正しいですか?

同じ stringstream 変数を複数回使用できますか?

私が試したとき、最初は大丈夫でしたが、それ以降はすべて0です。

4

5 に答える 5

6

それは間違いなくうまくいくはずです。以下に示すように、タイプを混在させることもできます。

string things = "10 Nawaz 87.87 A";
int i;
std::string s;
float f;
char c;

stringstream into;
into << things;
into >> i >> s >> f >> c; //all are different types!

cout << i <<"  "<< s <<"  "<< f <<"  "<< c;

出力:

10 Nawaz 87.87 A

ideone でのデモ: http://www.ideone.com/eb0dR

于 2011-02-20T05:24:17.427 に答える
1

あなたが投稿したものは、istringstream代わりに使用するJeremiah Willcockのソリューションとともに機能します。ただし、関数のscanfファミリも使用することを検討してください (int の数だけでは大きな違いはありませんが、より高度な入力では、scanf を使用すると、ストリーム マニピュレータをいじるよりもはるかに簡潔になります)。

string things = "10 11 12 -10";
int i1, i2, i3, i4, i5, i6;
sscanf(things.c_str(), "%d %d %d %d", &i1, &i2, &i3, &i4);

あなたの例がその後0を与える理由はstringstream、-10を抽出するとバッファが空になるためです。さらに抽出する前に、バッファにさらに挿入する必要があります。同じstringstreamインスタンスを複数回使用できますが、毎回バッファーを完全に使用するか、次のアイテムをバッファーに挿入する前にバッファーにさらに多くのアイテムがあることに気付く必要があります。

string things = "10 11 12 -10", temp;
int i1, i2, i3, i4;
stringstream into;
into << things; //buffer is now "10 11 12 -10"
into >> i1; //buffer is now " 11 12 -10"
into >> i2; //" 12 -10"
into >> i3; //" -10"
into >> i4; //""

//more code here...

//come back and use the instance again
into << "more: 1 2 3"; //"more: 1 2 3"
into >> temp; //temp is "more:"; into's buffer is " 1 2 3"
into >> i1; //buffer is " 2 3"

//more code here...

//reuse into once again
into << "4 5 6"; // buffer is now " 2 3 4 5 6"
into >> i1; //i1 gets the 2 from before, not the 4 just inserted; buffer now " 3 4 5 6"
into >> i2; //i2==3; buffer is " 4 5 6"

また、ios(継承元)演算子とキャストstringstreamも定義して、抽出が失敗したかどうかを簡単に確認できるようにします(またはが設定されているかどうかを技術的にチェックします。バッファに十分な量がない場合に一緒に設定されると思います):!void*failbitbadbitfailbiteofbit

string things = "10 11 12 -10";
int i1, i2, i3, i4;
stringstream into;
into << things;
into >> i1 >> i2 >> i3 >> i4;
if (into >> i5) {
    cout << "extraction to i5 succeeded" << endl;
}
if (!(into >> i6)) {
    cout << "extraction to i6 failed" << endl;
}
于 2011-02-20T05:28:37.500 に答える
1

それは機能しますか?私がそれを行う方法は次のとおりです。

istringstream into(things);
into >> i1;

等々。それはあなたが投稿した出力を生成します。

于 2011-02-20T05:18:32.977 に答える
0

2番目の質問について は、同じstringstream変数を複数回使用できますか?
おそらくclearseek再利用する前にストリームのが必要です。
たとえば、次のコードは2番目の質問に役立ちます。

int main() {
  string  s = "-1 2";
  stringstream  ss;
  ss << s;
  int i, j;
  ss >> i >> j;
  cout<< i <<' '<< j <<endl;
  ss.clear();
  ss.seekg( 0 );
  i = j = 0;
  ss >> i >> j;
  cout<< i <<' '<< j <<endl;
}

お役に立てれば。

于 2011-02-20T14:50:32.787 に答える
0

はい、動作します。
私が作る唯一の違いは次のとおりです。

string things = "10 11 12 -10";
int i1;
int i2;
int i3;
int i4;

stringstream into(things);    // Initialize in the constructor
into >> i1 >> i2 >> i3 >> i4; // Chain the inputs.

ラインストリームは通常のストリームと同様であり、最後を過ぎて読み取るとアイテムが不足し、失敗状態になることに注意してください。

stringstream into(things)
int val;
while(into >> val)                   // loop exits after 4 numbers as into.eof() 
{                                    // returns true after trying to read the 5 number.
    std::cout << "G(" << val << ")\n";
}

たとえば、4 つの数字で複数の行を読み取る場合は、次のようにします。

std::string  line;
while(std::getline(std::cin, line))
{
    /*
     * This way if a line is formatted incorrectly (only 3 numbers)
     * The error is local to the line and we will pick it up in linestream
     * without affecting the scanning of subsequent lines
     */
    std::stringstream linestream(line);

    int i1,i2,i3,i4;
    linestream >> i1 >> i2 >> i3 >> i4;
}
于 2011-02-20T07:23:30.617 に答える