-3

入出力ファイルについて調べています。以下のコードは、fgetc()、fgets()、fputs() などの関数に関連しています。思い通りに動かない理由がわかりません。どうもありがとうございました。以下は私のコードです:

#include <stdio.h>
int main()
{
   FILE *fp; //FILE type pointer
   int c; //using to get each character from file
   char buffer [256]; //array as buffer to archive string

    fp = fopen("file.txt", "r"); /*open a file with only read mode*/
   if( fp == NULL ) 
    {
      perror("Error in opening file");
       return(-1);
    }
     while(!feof(fp)) /*check if has not yet reached to end of file*/
     {
       c = getc (fp); //get a character from fp          
       if( c == '!' )
      {
         ungetc ('+', fp); //replace '!' by '+'

      }
      else
      {
         ungetc(c, fp); //no change
      }
       fgets(buffer,255,fp);//push string of fp to buffer
       fputs(buffer, stdout); //outputting string from buffer to stdout
    }
    return(0);
 }

4

4 に答える 4

2

while ループのロジックに欠陥があります。

これが起こることです:

あなたgetcは最初のキャラクター、a.

aではない!のでungetc a、ストリームに戻ります。

次に、行全体を読み取ります。もちろん、あなたは得るabc!!!

次に、行を印刷します。出力: abc!!!.

文字列を操作したい場合は、ストリームを変更しようとするのではなく、バッファを操作することをお勧めします:

   int i;
   int len = fgets(buffer,255,fp);//push string of fp to buffer
   for (i=0; i < len; i++) {
        if (buffer[i] == '!') {
             buffer[i] = '+';
        }
   }
   fputs(buffer, stdout); //outputting string from buffer to stdout

別の方法として、本当に を使用したい場合はungetc、一度に 1 文字ずつ読み取り/出力する必要があります。これは、1 文字でungetcしか安全に実行できないためです。ifと をそのままにして、 を次のようにungetc置き換えます。fgets/fputs

   fgets(buffer,1,fp);       // Read one character. 
   printf("%c", buffer[0]); // output one character from buffer to stdout
于 2016-07-25T07:53:25.313 に答える
0

別の回答で指摘されているように、一度に1バイトずつ取得してテストするのではなく、ファイルの最初の文字のみをテストし、そこから255バイトを読み取るため、エラーが発生します。

また、注意すべき重要なことは、ungetc はストリームにのみ影響し、ファイルには影響しないということです。

ただし、これはそのストリームの以降の入力操作にのみ影響し、それに関連付けられた物理ファイルの内容には影響しないことに注意してください。これは、この関数の呼び出しによって変更されることはありません。(cplusplus.com)

また、1 回の連続使用のみが保証されている場合の機能:

押し戻された文字は逆の順序で返されます。プッシュバックは 1 回だけ保証されます。(Linux マニュアル)

于 2016-07-25T07:51:25.160 に答える
0

ファイルの最初の文字を制御し、それがそうであるかどうかを制御するだけで!、そのストリームから255バイトを読み取り、出力ストリームにフラッシュします。

そのファイルから255バイトを読み取った後、入力ファイル(abc!!!あなたの例にあります)の場合、feof()はTrueを返し、読み取るものが何もないため、ループを中断します。

于 2016-07-25T08:02:09.653 に答える
-1

おそらく、ファイルを読み取り専用で開いているためです。

fp = fopen("file.txt", "r"); /*open a file with only read mode*/
于 2016-07-25T07:46:27.150 に答える