1

についてはたくさんの質問があることは承知していますが、scanfそれでも聞きたいことがあります。誰かがこの問題のルールまたは原則を説明してくれることを願っています:

最初のコード:

   #include <stdio.h>

   int main()
   {
           int c = 'W';
           while(c != 'F'){

                   scanf("%c",&c);
                   printf("c is : %c\n",c);
           }
           return 0;
   }

出力は次のとおりです。

E
c is : E
c is :                  <--newline

G
c is : G
c is :                  <---newline again

W
c is : W
c is :                  <---newline 

F
c is : F

さて、今でも理解できます。入力した改行はバッファにとどまり、アルファベットを押すたびに c を割り当てます。したがって、code2 を試します。

  #include <stdio.h>

   int main()
   {
           int c = 'W';
           while(c != 'F'){

                   scanf("%c\n",&c);   //<-- the only modified place.
                   printf("c is : %c\n",c);
          }
          return 0;
  } 

次に、この画面が表示されます。

E
G                        <---why the input and has one step before the output? 
c is : E         
W
c is : G
S
c is : W
C
c is : S
F
c is : C
R                       <---R was left in stdin, turn to a garbage, I didn't hope this. 
c is : F

stdinまた、 andをフラッシュしようとしましたがstdout、まだ使用できません。

:使用と対処するscanf("%c",c);別の方法でこれを修正できるかどうかはわかっていますが、混乱しました。code2の問題が発生した理由を理解したいと思っています。scanf("%c",&d);'\n'

以前に回答を確認しましたが、私は本当に慎重な人ではありません。この回答が本当に重複している場合、すべての反対票を理解できます。:)

前もって感謝します。

4

6 に答える 6

6

連続する空白の任意の組み合わせ (スペース、タブ、改行を含む) を scanf に渡すことは、「最初の非空白が発生するまで読み取る」ことを意味します (EOF を含む)。

2番目の例では、scanfは「E」を読み取り、改行を読み取り、空白以外が表示されるのを待ちます。

于 2013-08-10T23:32:30.877 に答える
2

そのため、(システム上では間違いなく、そして一般的に)ラインバッファリングされています。つまりstdin、「Enter」を押すまで、入力はプログラムに到達しません。これは、プログラム自体が「バックスペース」などを処理する必要がないことを意味します。

を使用する"%c\n"と、scanf入力後にのみ改行が受け入れられます。そこにない場合は、無視されます。

コメントで示唆されているように、"%c "「空白」をスキップします(改行、タブ、スペース、およびフォームフィードは「空白」としてカウントされると思います)。ただし、「不要な入力」として何かが入ることなく、「任意の入力」を1文字として読み取ることは保証されていません。scanf人間が入力した入力を読むのには絶対に適していません。柔軟性があり、さまざまな形式を処理できるため、マシンが生成したデータを読み取るのには適していますが、間違ったことを入力する人間にとっては、それほど優れていません。使用するfgets()(そしておそらくsscanf入力を解析するために、少なくとも「ユーザーがこの行に入力したものは、次回のラウンドで読み取られるのを待っている」タイプの驚き」を取得しないか、低レベルのシステムを使用します従属入力関数、ncurses

于 2013-08-10T23:35:34.390 に答える
1

最初の例ではscanf、 から一度に 1 文字を読み取るためstdinです。scanfそのため、ターミナルでは、ストリームからの抽出を開始するために空白文字を入力する必要があります。したがって、次のシーケンスを入力しているように見えます。

E, (new line), G, (new line), ...

...したがって、出力はあなたの例のようになります。

2番目の例でも同様に、文字の後に改行が続くことを除いて(scanf( "%c\n" )文字だけではなく、同じ理由です。

述べる:

次のテキスト ファイルをパイプした場合:

EGJKF

...その後、期待どおりの出力が得られます。

c is : E
c is : G
c is : J
c is : K
c is : F
于 2013-08-10T23:34:48.810 に答える
1

yeputons は、あなたが見ている動作の最良の説明を提供していると思いますが、実際の問題 (驚くべきことに、StackOverflow ではまだ見つけられませんでした) を解決するには、次の投稿を参照してください: http://classes.soe.ucsc.edu /cmps012a/Fall98/faq/scanfQ.html

scanf("%*[ \n\t]%c",&c);文字の前のすべての空白をスキップするを使用することをお勧めします。文字の後ろではなく前の空白をスキップすることで、さらなる入力を待つ必要がなくなります。

于 2013-08-10T23:35:22.567 に答える