C言語のプログラムにおいて,デフォルトの入力は,キーボードであり, デフォルトの出力は,コンソール画面である.これらを標準入力と標準出力と いう.C言語のプログラミングでは,以下の記述を使用する:
第1回目から,毎回使用してきた fgets の説明書きは以下のようになっ ている(man fgets より引用):
GETS(3) Linux Programmer's Manual GETS(3) 名前 fgetc, fgets, getc, getchar, gets, ungetc - 文字と文字列の 入力 書式 #include |
fgets は,ある入力からの文字入力を受け付ける.第3引数の FILE *stream が入力元である.標準入力を入力元とするときは,第3引数の値とし て,stdin を指定する.
fprintf の説明書きは以下のようになっている(man fprintfより引用):
int fprintf(FILE *stream, const char *format, ...); |
fprintf は,ある出力先にフォーマットに従って作られたテキストを出力 する.第1引数の FILE *stream が出力先である.標準出力に出力するときは, 第1引数の値として,stdout を指定する.
UNIX系での OS には,コンソールがある.コンソールは,コマンドを実行 する機能と,実行結果を画面に表示する機能がある.
コマンドを実行する機能は,「シェル」というインタフェースを介してい る.知能情報工学科の演習室のユーザの設定では,デフォルトで「bash(バッ シュ)」というシェルが使われている.「シェル」は,ファイルとコマンドの 間の情報のやりとりを支援する.
以下に,標準入力と標準出力を使用したプログラムの使用例を示す.
$ ./list0501 < f1.dat 23人分のデータを入力しました。 最高点は F.Alonso さんの 54 点でした。 平均点は 10.0 点でした。 |
データは,ここからダウンロードする.⇒ f1.dat
プログラムは,以下のとおり.
/* list0501.c */ #include <stdio.h> #define SIZ 100 int main() { char line[SIZ], name[SIZ * 2]; int s, p, max_s, max_p, tmp, num, sum; p = 0; // 名前を読み込む位置 max_s = -1; // 最高点 max_p = SIZ; // 最高点の名前の位置 name[max_p] = '\0'; // 最高点の名前を初期化 num = 0; // 入力した人数 sum = 0; // 合計点 while( fgets( line, SIZ, stdin ) != NULL ) { // 標準入力から1行読み込み. sscanf( line, "%s %d", &name[p], &s); // 名前と点を分ける. num += 1; // 入力した人数の加算 sum += s; // 入力した得点の加算 if( s > max_s ) { // もし最高点が入力されたならば, tmp = max_p; // max_p = p; // 名前を読み込む位置と最高点の名前の位置を swap p = tmp; // max_s = s; // 最高点の更新 } } if( num != 0 ) { // 0 で割り算をしないために fprintf( stdout, "%d 人分のデータを入力しました。\n", num ); fprintf( stdout, "最高点は %s さんの %d 点でした。\n", &name[max_p], max_s ); fprintf( stdout, "平均点は %3.1lf 点でした。\n", (double)( sum / num ) ); } else { fprintf( stdout, "入力がありません。\n" ); } return 0; } |
プログラムの実行結果をファイルに出力するのではなく,次に実行するプ ログラムの入力に直結させる機能が,シェルには用意されている.パイプ「|」を使う.
以下に使用例を示す.
$ grep ' 0' < f1.dat | sort -r |
f1.dat から 0 点の行を抽出し,アルファベットの降順にソートした結果をファイル"f1_zero.dat" に格納せよ.
$ grep ' 0' < f1.dat | sort -r > f1_zero.dat |
例題2からわかるように,パイプを使うとデータの加工が簡単に行える.データから特定の部分を抽出したり加工したりするプログラムをフィルタという.
f1.dat から点数が,L点以上,U点未満となる行を抽出するプログラムを作成せよ(動作例を以下に示す).
$ ./a.out 10 20 < f1.dat C.Klien 1 D.Coulthard 1 J.Villeneuve 6 M.Weber 6 N.Heidfeld 6 N.Rosberg 4 R.Barrichello 8 R.Schumacher 7 |
/* prac0501.c */ #include |
上記の課題を完成させて,1点以上20点未満の者を得点の降順にソートしてファイル f1_1_20.dat に出力するための実行方法,その実行結果,および,プログラムを示せ.実行時にはパイプと sort を使うこと.