0

テキスト ファイルの行を解析して、vector<string>. 私はJavaのバックグラウンドから来ており、C++がバッファの値に代入する方法について混乱しています。これが私のコードです:

string line;
vector<string> adsList;
ifstream inputFile;
inputFile.open("test.txt");
while(getline(inputFile, line))
{
    adsList.push_back(line);
}

Java では、データ構造に追加するときにオブジェクトのコピーが作成され、そのコピーが挿入されます。C ++では、データ構造は参照のみを保持するため、操作は非常に高速であると理解しています。C++ でやりたいことを実現する適切な方法は何ですか? 次のコードも試しました。

vector<string> adsList;
string line;
ifstream inputFile;
inputFile.open("test.txt");
while(getline(inputFile, line))
{
    string *temp = new string;
    *temp = line;
    adsList.push_back(*temp);
}

ここでの私の推論は、新しい文字列オブジェクトを作成して保存すると、各ループ反復が破棄された後もそれが保持されるということです。C++ はこれを Java とは正反対に処理しているようで、私は頭を悩ませています。

編集: test.txt は次のようになります。

item1 item1 item1
item2 item2 item2
item3 item3 item3
item4 item4 item4

各行を文字列として保存し、その文字列をベクター内に保存しようとしています。したがって、ベクトルの先頭には、値が「item1 item1 item1」の文字列が含まれます。

4

4 に答える 4

2

push_back()はコピーを作成するので、最初のコード サンプルはまさにあなたがやりたいことを実行します。実際、すべての C++ 構造体はデフォルトでコピーを格納します。コピーを取得しないようにするには、ポインターのコンテナーが必要です。

于 2012-11-26T05:22:29.723 に答える
1

コード全体を投稿していないため、これを試して、ファイルを読み取っているかどうかを確認することをお勧めします。

#include <iostream>
#include <fstream>
#include <vector>
using namespace std;

int main() {
  fstream inputFile("test.txt",fstream::in);
  string l;
  vector<string> v;
  while(getline(inputFile,l)) v.push_back(l);
  //Display the content of the vector:
  for(int i = 0; i < v.size(); ++i) {
    cout << v[i] << endl;
  }
  return 0;
}
于 2012-11-26T05:22:41.060 に答える
1

pointers参照に関するあなたの理解は正しくありませcopiesん-Javaの保存された参照、C++はあなたが要求したものを何でも保存します.

vector::push_backベクターに格納されているアイテムのコピーpointerを格納します。そのため、文字列を格納するためにヒープ上にnewメモリを作成する必要はありません。

(内部的に、いくつかのヒープ割り当てが行われていますが、それは の実装の詳細ですstd::string)

C++ にあるオプションpointers、むしろ を格納することであり、これらヒープに割り当てる必要があります。そうしないと、現在のスタック フレームがポップされたときに、ポインターが無効なメモリを指すことになります... しかし、それは別のトピックです。

コードの簡単な作業例については、こちらを参照してください。

#include <iostream>
#include <vector>
#include <fstream>

int main()
{
    std::vector<std::string> adsList;
    std::string line;
    std::ifstream inputFile;
    inputFile.open("test.txt");

    // read a line from the file - store it in 'line'
    while(getline(inputFile, line))
    {
        // store a *copy* of line in the vector
        adsList.push_back(line);
    }

    // for each element in adsList vector, get a *reference* (note the '&')
    for (std::string& s : adsList)
    {
        std::cout << s << std::endl;
    }

    exit(0);
}
于 2012-11-26T05:22:59.367 に答える
1

あなたの最初の仮定は間違っています。コピーは (一般に) に格納されますvector(C++11 で導入された移動操作は無視されます)。一般的に、これはあなたが操作したい方法です。

速度が本当に心配で、物事への参照 (実際にはポインター) を保存したい場合は、std::unique_ptrまたはのようなものを利用する必要がありますstd::shared_ptr。例えば:

std::vector<std::unique_ptr<std::string>> adsList;
std::string line;
inputFile.open("test.txt");
while(std::getline(inputFile, line)) {
    adsList.push_back(std::unique_ptr<std::string>(new std::string(line));
}

通常、これは、コンテナー内の値を変更し、その変更を元のオブジェクトに反映させる必要がある場合にのみ行われます。この場合は、std::shared_ptr. 最も一般的なシナリオは、最初のコード例です。

于 2012-11-26T05:23:54.757 に答える