C/C++エラー:char c=getchar();


多くの初心者はchar型変数でgetchar、getc、fgetcなどの関数の戻り値を受信することに慣れているが、実際にはそれは間違っており、致命的なエラーが隠されている.getcharなどの関数の戻り値のタイプはすべてint型で、これらの関数の読み取りエラーやファイルの読み取りが完了するとEOFに戻る.EOFはマクロであり、標準ではその値がint型の負数定数でなければならないことを規定している.通常、コンパイラはEOFを-1と定義する.問題はここで,char型変数を用いてgetcharなどの関数の戻り値を受信すると,EOFの認識エラー,あるいは良いデータをEOFと誤認したり,EOFを良いデータと誤認したりすることである.例: int c;  /* 。 int fgetc */
        while ( (c = fgetc(fp)) != EOF )
        {
            putchar(c);
        }
 

上記の例のように、fgetcなどの関数の戻り値を1つの変数で受信してから、この変数をEOFと比較して、ファイルが読み終わったかどうかを判断する必要がある場合が多い.上記の例は正しいが,cをint型として定義することで,fgetcが返すEOFを正しく受信できることを保証し,この比較の正確性を保証した.しかし,cをchar型と定義すると,思わぬ結果を招く.
まず、fgetcなどの関数の戻り値はint型であるため、char型変数に値を割り当てると劣化し、データが遮断される.例:
   ---------------------------------
|十進|int|char|
   |--------|--------------|-------|
   |   10   | 00 00 00 0A  |   0A  |
   |   -1   | FF FF FF FF  |   FF  |
   |   -2   | FF FF FF FE  |   FE  |
   ---------------------------------
ここで,intとcharはそれぞれ32ビットと8ビットであると仮定する.上の表から,int型からchar型まで3バイトのデータが失われた.char型とint型を比較すると、char型は自動的にint型にアップグレードされます.char型がint型にアップグレードされた値は、signed charなのかunsigned charなのかで異なります.残念なことに、signedまたはunsignedを使用してcharを修飾していない場合は、コンパイラによって決定されるため、charがunsigned charを指すのかsigned charを指すのか分からない.ただし,charがsignedであろうとunsignedであろうと,char型変数を用いてfgetcなどの関数を受信する戻り値が間違っているという事実は変えられない.唯一変えられるのは、このエラーによる結果です.前述したように、char型とint型を比較すると、charは自動的にintにアップグレードされます.次に、signed charとunsigned charがintに変換された後、それらの値がどのように異なるかを見てみましょう.