第十三章 scanf


scanf                                                                                                               
scanf 関数は、printf 関数の入力版で、プログラムを組むときにデータを入力するのではなく、
プログラムを実行している最中にデータを入力することができます。

<scanf>
#include<stdio.h>
main()
{
    int a;
    printf("aに何(整数のみ)を代入しますか?\n");
    scanf("%d",&a);    /* 画面に入力されるものが%d型だとして、それを箱aに入れています */
    printf("aには%dが入っています",a);
}
<実行結果>
aに何(整数のみ)を代入しますか?
10
aには10が入っています

<実行結果>では、「aに何(整数のみ)を代入しますか?」のあとに、
10と入力してリターンを押しています。
すると、scanf の %d が 10 となり、箱aに10が入れられます。

ここで、注意しなければならないのは、入力する型は必ず合わせなければならないということです。
printf 関数と同様、必ずデータの型を合わせないと思った通りに処理してくれません。

つまり、int 型を扱うなら %d、float,double 型なら %f,%lf、char 型なら %c,%s を用いるのです。

scanf 関数の引数に&がつく理由
                                                                                             
結論から言うと、scanf 関数はいろいろなデータを受け取れるように、
受け取る箱(引数)はポインタ(アドレス)になっているのです。

例えば文字列を受け取るとき、ポインタでなければ文字数をあらかじめ知っている必要があります。
文字列の文字1つを入れられる箱を、いくつ用意すればいいのかわからないからです。

一方、文字列を受け取るとき、ポインタであれば文字数をあらかじめ知っておく必要はありません。
文字列の先頭アドレスさえわかれば、第二章で説明した文字列の終了を示す \0 がでてくるまで、
ポインタを1つずつ進ませればよいのです。

このような理由により、scanf 関数が受け取る引数はポインタ変数になっているのです。


さて、今の説明を読んだなら、プログラム中の scanf 関数の a に
アドレス演算子 & がついている理由がわかると思います。

つまり、scanf 関数で、アドレス演算子をつけるということは、
scanf 関数は引数をポインタ(アドレス)として受け取っていることになります。


以上のことから、文字列を扱うときには少し注意が必要です。
次のプログラムを見てください。
<文字列を扱うときのscanf>
#include<stdio.h>
main()
{
    char a[11];
    printf("何か文字列を入力してください(5文字以内で)\n");
    scanf("%s",a);
    printf("入力された文字は“%s”です",a);
}
<実行結果>
何か文字列を入力してください(5文字以内で)
あいうえお
入力された文字は“あいうえお”です

scanf 関数の引数に & がついてないことに注意してください。

これは、第十一章ポインタ配列で説明したとおり、
配列名はその配列の先頭アドレスを表すからです。

もちろん、scanf の部分を
            scanf("%s",&a[0]);
としても全然OKですが、上のプログラムのように、
            scanf("%s",a);
とする方が一般的です。

文字列を入れる変数を、a[10] ではなく a[11] のように、1 多くしているのは、
すべて日本語を入れたときでも、文字列の終了を示す \0 を入れられるようにするためです。

<前に戻る  |目次|  次へ進む>