5

C から C++ に変換する電話帳アプリのファイルの最後まで読み取ろうとしています。ファイルから結果を印刷すると、次のようになります。

johnny smith
(Home)3
(Cell)4
x☺> x☺>
(Home)4
(Cell)4

それは印刷する必要があります:

johnny smith
(Home)3
(Cell)4

現在、私while(!infile.eof())が読んだものを使用しているのは悪い習慣ですが、使用するinfile.getline()と、姓と名が繰り返され、フォーマットがすべてジャッキアップされます。とにかく(または別の方法で)入力の最後にジャンクを取り除くか、これを修正するC ++でファイルの最後まで読み取る別の方法がありますか。私はさまざまな解決策について読んできましたが、多くのサイトが同意しているように見えるのは ですfgets。これは、元の C バージョンで使用していたものですが、私が使用しているものでは明らかにfgets機能しません。ifstreamコードは次のとおりです。

void contacts:: readfile(contacts*friends ,int* counter, int i,char buffer[],char    user_entry3[])
{
   ifstream read;
   read.open(user_entry3,ios::in);
   int len;
   contacts temp;
   *counter=0;
   i=0; 

     while (!read.eof()) { 
       temp.First_Name=(char*)malloc(36); 
       temp.Last_Name=(char*)malloc(36); 

       read>>temp.First_Name>>temp.Last_Name;

       read>>buffer;
       len=strlen(buffer);
       if(buffer[len-1]=='\n')
          buffer[len-1]='\0';

       temp.home=(char*)malloc(20); 
       strcpy(temp.home, buffer);

       read>>buffer;
       len=strlen(buffer);
       if(buffer[len-1]=='\n')
       buffer[len-1]='\0';


       temp.cell=(char*)malloc(20); 
       strcpy(temp.cell, buffer); 

      friends[i].First_Name=(char*)malloc(MAXNAME);
      friends[i].Last_Name=(char*)malloc(MAXNAME);
      friends[i].home=(char*)malloc(MAXPHONE);
      friends[i].cell=(char*)malloc(MAXPHONE);


  //adds file content to the structure
      strcpy(friends[*counter].First_Name,temp.First_Name);
      strcpy(friends[*counter].Last_Name,temp.Last_Name);
      strcpy(friends[*counter].home,temp.home);
      strcpy(friends[*counter].cell,temp.cell);


     (*counter)++;
     i++; 

   }
   //closes file and frees memory
    read.close();
    free(temp.Last_Name);
    free(temp.First_Name);
    free(temp.home);
    free(temp.cell);
}
4

2 に答える 2

7

ファイルの終わりに達したかどうかを判断するために使用しないでください。eof()代わりに、読み取りたいものを読み取り、データを正常に読み取れたかどうかを確認しますObce reading failed を使用eof()して、フォーマット エラーに関するエラー レポートを作成する前に、エラーがファイルの最後に達したかどうかを判断できます。

使用することは良い習慣であると読んだと!infile.eof()おっしゃいましたが、この間違った情報のソースを教えていただけますか? この情報は修正が必要です。

于 2012-11-24T18:36:37.053 に答える
7
  1. 使用しないでください!eof()最後の読み取りエラーがファイルの終わりに達したことが原因であるかどうかを確認します。未来を予測するものではありません。

  2. mallocC++ では使用しないでください。その場合は、戻り値でエラーを確認してください。

  3. operator>>には使用しないでくださいchar *。サイズ チェックがないため、バッファ オーバーフローを要求しているだけです。

  4. バッファの'\n'チェックは役に立ちません。operator>>文字列の場合、空白で停止します。

  5. strcpy長さ不明の文字列を盲目的temp.homeにサイズ 20 にしています。これは別のバッファ オーバーフローです。

  6. …そこで読むのをやめました。ファイルから内容を読み取りたいが、eof/error で停止する場合は、次のようにすることができます。

.

string a, b, c;
while (true) {
    if (!(in >> a)) break;
    if (!(in >> b)) break;
    if (!(in >> c)) break;
    do_stuff_with(a, b, c);
}
于 2012-11-24T18:40:33.747 に答える