FrontPage  ページ一覧  検索  更新履歴  RSS  ログイン

Psychlops Wiki - (Tips) Traps in integer types 差分

  • 最後の更新で追加された部分はこのように表示します。
  • 最後の更新で削除された部分はこのように表示します。

! 数値型の昇格とは

!! キャスト(型変換)
コンピュータ言語においてキャストとは、(変数や定数を)型を別の精度の型に変換することをさします。あくまでキャストを命令した式の計算途中でだけ別の型に変換するだけで、もともと変数の中身は型変換されません。

!! 自動昇格
C++では、精度の異なる型どうしを演算しようとした場合、自動的に「強い」(表現範囲が広い)型のほうにキャストされます。たとえば、以下のコードでは ( a + b ) のaは整数(int)でbは浮動小数点(double)ですが、コンパイラは型の表現範囲が広い浮動小数点にそろえて加算を行い、浮動小数点の解を返すよう自動的にキャストを行います。

{{syntax_highlight('cpp')}}
<<<
int a;
double b, c;
c = a + b
>>>



! 昇格忘れ

C++では、整数型(int)どうしで演算するとその項の演算結果は整数型になります。これが原因で、比率の計算などで思わぬバグを生む場合があります。例として、[0,1]の範囲の比率を配列に次のようなコードを考えます。

{{syntax_highlight('cpp')}}
<<<
const int MAX;
double result[MAX];
for(int i=0; i<MAX; i++) {
    result[i] = i / (MAX-1);
}
>>>

このコードを実行すると、配列resultの中身はすべて0になります。整数型どうしの割り算は自動的に小数点以下切捨てとなるため、[0, 1)の範囲はすべて0になってしまいます。これを防ぐには、以下のように関係する変数をdouble型にキャストしておく必要があります。

{{syntax_highlight('cpp')}}
<<<
const int MAX;
double result[MAX];
for(int i=0; i<MAX; i++) {
    result[i] = (double)(i) / (MAX-1);
}
>>>

double型とint型を演算した場合、コンパイラによってdouble型どうしの演算に読みかえられます。

演算優先順位{{fn("たとえば
a * b + c
という式では、まず項 a * b が計算され、次に(a*b) + cの項が実行されます。")}}の高い項を事前にdouble型にキャストしておく必要があります。