2016-04-16 11 views
0

ファイルからアイテムに関する情報を読み取るプログラムがあります。問題は、「G ***。DTA」と呼ばれるさまざまなファイルにアイテムが散在していることです(*** =アイテムカテゴリの一意の番号、「G34.DTA」)。C++同じ関数内のさまざまなテキストファイルからの読み取り

これらのファイルを読むには、for-loopを使用してすべてのカテゴリ番号を参照する関数を作成しました。 forループの反復変数は、作成したifstreamオブジェクトのファイル名を作成するために使用されます(第1ラウンドG1.DTA、第2ラウンドG2.DTAなど)。また、すべてのカテゴリにファイルがあるわけではないので、「欠落している」ファイルがいくつかあります。ですから、私のプログラムはG2.DTA、G5.DTA、G10.DTAなどを持つことができます。他のすべてはスキップする必要があります。

とにかく、ファイルから読み込もうとすると、プログラムがハングするだけです。ファイル関数、コンストラクタ、およびファイル形式からの読み込みを含めると、私のミスがどこにあるのか誰にでも見えますか?

この関数は、ファイルから読み込む必要があります。

void Items::readItemsFromFile() { 
    for(int i = 1; i <= categoryBase->lastCategoryInUse; i++) { 
     char filename[STRLEN]; 
     char buffer[10]; 
     int nr; 
     itoa(i, buffer, 10);           // Makes category number a char for strcat() 
     strcpy(filename, "G");           // Makes "G" first part of filename 
     strcat(filename, buffer);          // Makes category number (i) second part of filename 
     strcat(filename, ".DTA");          // Makes ".DTA" suffix of filename 
     ifstream infile(filename); 

     if(infile) { 
      infile >> nr; 
      while(!infile.eof()) { 
       itemList->add(new Item(nr, infile)); 
       infile >> nr; 
       } 
      } 
     } 
    } 

は、ここで(int型nは親クラスNumElementに送信され、項目番号として設定されている)コンストラクタです:

Item::Item(int n, ifstream & in): NumElement(n) { 
    char buffer[STRLEN]; 

    in.getline(buffer, STRLEN); 
    salesman = new char[strlen(buffer) + 1]; strcpy(salesman, buffer); 
    in.getline(buffer, STRLEN); 
    title = new char[strlen(buffer) + 1]; strcpy(title, buffer); 
    in.getline(buffer, STRLEN); 
    description = new char[strlen(buffer) + 1]; strcpy(description, buffer); 
    in >> startTime >> endTime >> startPrice >> shipping >> increaseBid >> lastBid >> bidTime; in.ignore(); 
    } 

そして、ここではどのようですファイル形式は次のようになります:

1 
van gogh 
summer 
beautiful painting 
1 2 100 33 5 0 0 
3 
da vinci 
mona lisa 
classic 
2 3 50 20 3 0 0 
+3

'std :: string'はそれほど醜くエラーを起こしやすいでしょう。 –

+3

あなたはC++を書いています。単にstd :: stringを使用しないのはなぜですか?また、charバッファを宣言することが頻繁に繰り返される間違いを、正しいバイト数とみなしています。現在、その文字列がNULLを含むSTRLEN文字以上の場合、メモリ上書きエラーが発生します。 std :: ostringstreamとstd :: stringが使用されていれば、これはすべて問題になる可能性があります。 – PaulMcKenzie

答えて

0

infile >> nr;で整数を読んだ後に読みは(あなたのファイル構造に応じて)改行文字で止まるのでgetline()を使用してファイルから行を読み取るために開始する前に、あなたはifstream::ignore()を呼び出す必要があります。そうでない場合は、ifstream::getline()は、ストリームをに設定すると文字が読み込まれず、状態になり、それ以上の読み込み操作は成功しません(したがって、ファイルの最後に到達すると無限ループの繰り返しになります)。

私はstd :: stringを使用する必要があります。あなたのコードを改善するのに役立つ追加のメモについては、あなたの質問のコメントのセクションも見てください。

+0

ありがとう、それは問題でした!しかし何らかの理由で、プログラムは最初のエントリだけを読み込み、エラーを返します。どんな手掛かり? c-stringの使用について:文字列に進む前に、c-strings/char配列がどのように動作するかに関する基本的な知識を得ようとしています。しかし、チップのおかげで! –

+0

最初のエントリーはどういう意味ですか?そしてそれはどのようなエラーですか? –

+0

申し訳ありませんが、実際には最後のエントリです。エントリーでは、私はアイテムリストにエントリーを意味します。プログラムを実行すると、ファイルから読み込まれ、エントリ(項目)のリスト全体が表示されますが、最後のものだけが表示され、「Auction.exeで未処理のWin32例外が発生しました[8944] "。 –

0

std :: ifstream :: ignore(デフォルトはeofを無視する)は、Itemコンストラクタの最後の実行時(ファイルから最後に読み込まれた項目)のストリームを無視しますか?

関連する問題