2. データを格納するための変数(2/2)
2.2 基本的な入出力方法
変数とデータの入出力は直接の関係は無いのですが、入出力が出来ないと例題のプログラムが作成しにくいので、ここで簡単なデータの入出力の方法について説明します。
UNIX系OSには標準入出力という機能があり、これを利用するとキーボードからの入力やターミナルへの出力が簡単に行えます。また、シェルの機能のリダイレクションやパイプラインは標準入出力を対象としていますので、標準入出力への入出力が出来ればこれらの機能が使えます。例えば、ターミナルに出力しているメッセージをファイルに保存したい場合や、他のコマンドに渡したいような場合も、リダイレクションやパイプラインの機能を使えばプログラムを変更しなくても対応できます。
C言語での入出力はライブラリと呼ぶプログラム部品が提供されていますので、通常は、これらのプログラム部品を使います。このプログラム部品は関数と呼ぶ形式で作成されていますので、入出力を行いたいところで、入出力関数を呼び出します。
ライブラリ関数を使う場合の注意点として、ヘッダファイルと呼ぶファイルを取り込む必要があります。ヘッダファイルには関数の定義情報や、関数を使うのに必要なデータが定義されています。入出力関数の場合はstdio.hファイルを取り込みます。(ファイルの取り込みに付いては「13. プリプロセッサ」をご覧ください)
ここでは、入出力関数として例題などによく使われている2つの関数の使い方を説明します。
2.2.1 ターミナルへのデータ出力(標準出力)
ターミナルへメッセージを出力するにはprintf関数を使用します。この関数は最初に紹介したHello Worldプログラムで使っていました。printf関数は標準出力へ出力を行う関数です。
形式
printf関数の形式は大きく分けると次の2種類になります。最初の形式は出力したいメッセージが固定の場合に使用し、2番目の形式は変数の値を出力する場合に使用します。出力する内容によって、使い分けが必要です。
※ メッセージが固定の場合
printf("出力文字列");
※ 変数の値を出力する場合
printf("書式制御文字列と出力文字列", 変数名);
- 出力文字列
- 出力する内容を指定します。"(引用符)で括りますので注意してください。
- 書式制御文字列と出力文字列
- 変数の値の編集形式を指定するための書式制御文字列と出力文字列を指定します。書式制御文字列は変数の値に置き換えられます。書式制御文字列の種類は沢山ありますが、ここでは例題プログラムで使う程度の簡単なもののみ説明します。
- %c
- char型の変数の値を編集します。
- %d
- short intとint型の変数の値を編集します。
- %f
- floatとduble型の変数の値を編集します。標準では小数点以下6桁まで出力します。小数点以下の桁数を指定したい場合は「%.nf」の形式になります。(nは小数点以下の桁数です)
- 書式制御文字列以外の文字列
- そのまま出力します。
- 変数名
- 出力したい変数の名前(変数名)を指定します。複数の変数を指定する場合は,(コンマ)で区切ります。なお、変数の型と書式制御文字列は一致している必要があります。
文字の定数は'(アポストロフィ)で括る場合と、"(引用符)で括る場合があります。使い分けの詳細は後ほど説明します。(7.3 文字列の取扱い)
例題
この例題プログラムでは変数を使う必要性は無いのですが、printf関数の使い方を説明するために変数を使っています。
#include <stdio.h>
int main()
{
int nenrei = 13;
double taijyu = 18.5;
char ketueki = 'A';
printf("私のプロフィルです。\n");
printf("・年齢:%d歳\n", nenrei);
printf("・体重:%fKg\n", taijyu);
printf("・血液型:%c\n", ketueki);
return 0;
}
- 1行目
- ヘッダファイル(stdio.h)を取り込みます。
- 4〜6行目
- 変数を宣言します。
- 8行目
- printf関数で「私のプロフィルです。」を標準出力に出力します。\nは改行を指示します。
- 9行目
- %d書式制御文字列を使って、変数nenreiの値を標準出力に出力します。書式制御文字列以外の文字はそのまま出力しますので、「・年齢:13歳」を出力します。変数nenreiはint型ですので書式制御文字列は%dになります。
- 10行目
- %f書式制御文字列を使って、変数taijyuの値を標準出力に出力します。書式制御文字列以外の文字はそのまま出力しますので、「・体重:18.500000Kg」を出力します。変数taijyuはdouble型ですので書式制御文字列は%fになります。
- 11行目
- %c書式制御文字列を使って、変数ketuekiの値を標準出力に出力します。書式制御文字列以外の文字はそのまま出力しますので、「・血液型:A」を出力します。変数ketuekiはchar型ですので書式制御文字列は%cになります。
コンパイルして実行します。
$ gcc -o ex02_2.prg ex02_2.c
$ ./ex02_2.prg ← 実行します
私のプロフィルです。
・年齢:13歳
・体重:18.500000Kg ← 書式制御文字列%fは小数点以下6桁で出力します
・血液型:A
$
$ ./ex02_2.prg > profil.txt ← 出力先をprofil.txtに切り替えます
$ cat profil.txt
私のプロフィルです。
・年齢:13歳
・体重:18.500000Kg
・血液型:A
$
$ ./ex02_2.prg | wc -l ← 出力をパイプラインでwcコマンドに渡して行数をカウントします
4
$
2.2.2 キーボードからの入力(標準入力)
キーボードからデータを変数に入力するにはscanf関数を使用します。scanf関数は標準入力から入力を行う関数です。なお、この関数はバッファオーバフローと呼ぶ、セキュリティ上重大な問題を起こす可能性がありますので、使用は例題プログラムや実験的なプログラムにとどめ、業務プログラムには使わない方がよいでしょう。
形式
scanf関数は入力したデータをどのような型のデータとして変数に格納するかを、書式制御文字列で指定します。
scanf("書式制御文字列", &変数名);
- 書式制御文字列
- ここでは、例題プログラムで使う程度の簡単なもののみ説明します。
- %c
- char型の変数に1文字入力します。入力データ中の空白文字(スペース、改行、タブ、等)は読み込みます。
- %d
- int型の変数に整数として入力します。入力データ中の空白文字は区切りとして読み飛ばします。
- %f
- float型の変数に浮動小数点数として入力します。入力データ中の空白文字は区切りとして読み飛ばします。
- %lf
- double型の変数に浮動小数点数として入力します。scanf関数の場合は、float型とdouble型で書式制御文字列が異なりますので注意してください。入力データ中の空白文字は区切りとして読み飛ばします。
- &変数名
- &(アンパサンド)の次に入力したデータを格納する変数を指定します。複数の変数を指定する場合は,(コンマ)で区切ります。なお、変数の型と書式制御文字列は一致している必要があります。
&(アンパサンド)は演算子の一種です。詳細については後ほど説明します。(8.2 ポインタ変数の宣言)
例題
キーボードから年齢・体重・血液型を入力して、結果をターミナルに出力するプログラムです。
#include <stdio.h>
int main()
{
int nenrei;
double taijyu;
char ketueki;
char dummy;
/* 年齢、体重、血液型の入力 */
printf("年齢を入力してください ==> ");
scanf("%d", &nenrei);
printf("体重を入力してください ==> ");
scanf("%lf", &taijyu);
scanf("%c", &dummy); /* 改行文字を入力 */
printf("血液型を入力してください ==> ");
scanf("%c", &ketueki);
/* プロフィルの出力 */
printf("\nあなたのプロフィルです。\n");
printf("・年齢:%d歳\n", nenrei);
printf("・体重:%.1fKg\n", taijyu);
printf("・血液型:%c\n", ketueki);
return 0;
}
- 1行目
- ヘッダファイル(stdio.h)を取り込みます。
- 9、18行目
- コメント行です。「/*」と「*/」の間にはコメント(注釈)を記述することができます。コメントはプログラムの実行に影響しません。
- 10、12、15行目
- 入力を促すためのメッセージを出力します。改行指定をしていません。
- 11行目
- %d書式制御文字列を使って、変数nenreiに整数の値を入力します。
- 13行目
- %lf書式制御文字列を使って、変数taijyuに浮動小数点数の値を入力します。
- 14行目
- %c書式制御文字列を使って、変数dummyに1文字入力します。ここで入力しているのは体重を入力したときの改行文字です。%cは空白文字も入力してしまいますので注意してください。
- 16行目
- %c書式制御文字列を使って、変数ketuekiに1文字入力します。
- 19行目
- 「あなたのプロフィルです。」の前後に\n(改行文字)が入っていますので、メッセージの前と後で改行します。
コンパイルして実行します。
$ gcc -o ex02_3.prg ex02_3.c
$ ./ex02_3.prg
年齢を入力してください ==> 13 ← 「1、3、改行」を入力します
体重を入力してください ==> 18.5 ← 「1、8、.、5、改行」を入力します
血液型を入力してください ==> A ← 「A、改行」を入力します
← 空行です
あなたのプロフィルです。
・年齢:13歳
・体重:18.5Kg
・血液型:A
$