数値変数・数式・書式付き入出力の適切な使い方を理解しよう. そして,単純な数値データ処理プログラムを作成してみよう.
いつもの通り,作業用ディレクトリを準備しよう:
$ cd $ mkdir c-0509 $ cd c-0509
データ処理プログラムの段取りの基本形は次の通り:
書式付き入力 scanf() を利用して, キーボードからデータを入力し, 入力されたデータを変数に格納する. なお,変数の利用には事前準備が必要であり, ソースの先頭付近で型と名前を宣言しておく.
コード例:
#include <stdio.h> // scanf() に必要 int main(void) { int num; // 整数型の変数 num を宣言 // 「後で num を使うよ,整数を代入できるよ」 double val; // 実数型の変数 val を宣言 // 「後で val を使うよ,実数を代入できるよ」 ... scanf("%d %lf", &num, &val); // 最初に %d で整数,次に空白,最後に %lf で実数, // というパターンでキーボードから入力してね. // 変数 num に整数,val に実数が格納されるよ. // 変数名の前「&」の付け忘れに注意!! ... }
数式等を利用して,目的のデータ処理を実行する.
コード例:
... int main(void) { double total; ... total = num*val; // かけ算 num*val を計算し,計算結果を変数 total へ代入してね. ... }
計算結果のデータにも型があることに注意しよう.
書式付き出力 printf() を利用し, 端末画面に計算結果等を表示する.
コード例:
#include <stdio.h> // printf() に必要 int main(void) { ... printf("%d * %f = %f\n", num, val, total); // 文字や数値を端末画面に表示してね. // %d は整数 num,%f は実数 val とtotal の値に置き換わるよ. ... }
printf() と scanf() の書式について, %f と %lf のように, 微妙な違いがあることに注意しよう.
なお,C言語の世界では, 整数データと実数データとは明確に区別されている. たとえば,整数 123 と実数 1.23×102 は互いに別物となる. 数値的に,ほぼ等しいかもしれないが,完全に一致するとは限らない.
また,取り扱い可能な数値の範囲に制限がある. 計算結果のオーバーフロー等に注意しよう.
int型の整数データ1個あたりの情報量は, 4 byte(16進数8桁)=32 bit(2進数32桁)であり, 表現可能な数値の範囲は 0 〜 232ー1 ≒ 約40億となる. ただし通常は,負数も使うので,範囲はー約20億 〜 +約20億となる.
ソースを編集:
$ vim int.c # エディタは何でも OK
#include <stdio.h> int main(void) { int x, y, z; // 整数型の変数 x,y,z の宣言 while (1) { // 繰り返し printf("整数2個 > "); scanf("%d %d", &x, &y); // 入力 z = x * y; // 計算(かけ算) printf("%d * %d = %d\n", x, y, z); // 出力 } return (0); }
コンパイルと実行:
$ cc int.c -o int
$ ./int
整数2個 > 35 100
35 * 100 = 3500 # そだねー
整数2個 > 3500 1000000
3500 * 1000000 = -794967296 # えっ??
整数2個 > [Ctrl]+[C] # 強制終了
double型の実数データ1個あたりの情報量は 8 byte, 数値範囲は±約1.0×10±308, 有効数字は15桁となっている.
double.c:
...#include <stdio.h> int main(void) { double x, y, z; // 実数型の変数 x,y,z の宣言 while (1) { printf("実数2個 > "); scanf("%lf %lf", &x, &y); // 入力 z = x / y; // 計算(わり算) printf("%f / %f = %f\n", x, y, z); // 出力 } return (0); }
$ ./double 実数2個 > 1 3 1.000000 / 3.000000 = 0.333333 実数2個 > 2.0 1.41421356 2.000000 / 1.414214 = 1.414214 実数2個 > 1 0 1.000000 / 0.000000 = inf # inf は infinity...無限ね 実数2個 > 0 0 0.000000 / 0.000000 = -nan # nan って何?not a number...不定値,非数
(型の指定)
(幅の指定)
実験:書式指定をわざと間違えてみよう.format.c:
#include <stdio.h> int main(void) { int x = 123; double y = 123.45; printf("正:\n"); printf("x = %d\n", x); printf("y = %f\n", y); printf("誤:\n"); printf("x = %f\n", x); // 整数型は %d のハズ printf("y = %d\n", y); // 実数型は %f のハズ return (0); }
実行結果はどうなる?
変数の値を使用して何かを計算する場合, 事前に初期化(初期値を代入 or 入力)しておく必要がある.
実験:変数をわざと初期化せずに使ってみよう.var.c:
#include <stdio.h> int main(void) { int x, y, z; // 初期化しないと... printf("%d %d %d\n", x, y, z); // どんな値? return (0); }
ゴミ(無意味な値)が入っている. また,実行しなおす度に異なる結果となる.
実行例:
$ ./d2x 10進数 > 255 16進数 = FF 10進数 > 16 16進数 = 10 ...
要求仕様:次の動作を永久に繰り返す:
実行例:
$ ./x2dq 16進数を10進数に変換しなさい. 0x67 > 100 ☓ :正解は 103 です. 0xC6 > 198 ◯ 0x69 > 105 ◯ . . .
提出: