コンピューターは、無限の大きさを持つ値や、無限に小さい(限りなく0に近い)値はもちろんですが、非常に大きい値や、小さい値も記憶できません。その限度の値は、データ型の違いによって決まります。
オーバーフローやアンダーフローが発生すると、当然数値計算の結果にも影響します。数値計算の実行結果がおかしければ、オーバーフローやアンダーフローが発生している可能性があります。
オーバーフローとアンダーフロー
コンピューターは、非常に大きい値や小さい値は記憶できない
単精度浮動小数点変数のオーバーフローを調べる
以下は、単精度の浮動小数点変数にオーバーフローを発生させ、どのくらいの最大値まで表現できるのか調べるプログラムソースコード例です。
#include <stdio.h>
int main(void)
{
int i;
int N;
float num = 1.0;
printf("N = ");
scanf("%d", &N);
/* 2のN乗を計算し表示する */
for(i = 1 ; i <= N ; i++)
{
num *= 2.0;
printf("%d %f\n", i, num);
}
return 0;
}
数値計算実行結果
上記のプログラムをコンパイルし実行し、N の値を入力すると、以下のような結果が表示されます。
N = 128 1 2.000000 2 4.000000 3 8.000000 省略 126 85070591730234616000000000000000000000.000000 127 170141183460469230000000000000000000000.000000 128 1.#INF00ここでは、N を 128 としました。結果を見ると、2の128乗以上の値は表現できない事がわかります。ちなみに、1.#INF00 は、浮動小数点型変数がオーバーフローを起こしている事を意味しています。
単精度浮動小数点変数のアンダーフローを調べる
以下は、単精度の浮動小数点変数にアンダーフローを発生させ、どのくらいの最小値まで表現できるのか調べるプログラムソースコード例です。
#include <stdio.h>
int main(void)
{
int i;
int N;
float num = 1.0;
printf("N = ");
scanf("%d", &N);
/* 2の-N乗を計算し表示する */
for(i = 1 ; i <= N ; i++)
{
num /= 2.0;
printf("%d %e\n", i, num);
}
return 0;
}
数値計算実行結果
上記のプログラムをコンパイルし実行し、N の値を入力すると、以下のような結果が表示されます。
N = 150 1 5.000000e-001 2 2.500000e-001 3 1.250000e-001 省略 148 2.802597e-045 149 1.401298e-045 150 0.000000e+000
ここでは、N を 150 としました。
結果を見ると、2のー150乗未満の値は表現できない事がわかります。また、アンダーフローが発生すると、0になるという事もわかります。
2009/04/25 更新
