2012-07-25 23 views
9

Range CheckエラーとOverflowエラーの両方を引き起こすコードの圧縮バージョンです。これらのコンパイラチェックディレクティブを有効にする必要があります。なぜこれがオーバーフローを引き起こすのか理解しています。C1の乗算では、データ型の最大値を超える可能性があります。しかし、なぜこれもRange-checkエラーを引き起こすでしょうか? Delphiのドキュメントやスタックオーバーフローに関するその他の記事では、範囲チェックエラーは通常、範囲外の配列アクセスのために発生します。しかし、私はレンジチェックエラーの原因となっている行の配列にアクセスしていません。おそらくparam1への割り当てに?しかし、なぜそれが範囲チェックで、オーバーフローエラーではないでしょうか?Range Check Error(デルファイ)の原因

const 
    C1 = 44001; 
    C2 = 17999; 

function fxnName(..other params...; param1: Word): String; 
var 
    someByte: byte; 
begin 
    // some code 
    // by now we're in a loop. the following line is where it breaks to in the debugger: 
    param1 := (someByte + param1) * C1 + C2; 
    // more code 
end; 

それは、関連するなら、それはデバッガでその行に分割したときに予想されるように、すべての値が「未定義の識別子: 『PARAM1』」を示しPARAM1、を除いて、見て、私はそれを評価するためにデルファイを要求したとき。

+0

私は範囲チェックがオーバーフローチェックの前に発生したからといって、それはだ疑いがある、と思い範囲に一度チェック例外が発生した場合、オーバーフローチェックは発生しません。 (順序がわからないので疑いの余地があります。) –

答えて

17

範囲チェックの状態に関する文書:

の$ R指令は、レンジチェックコードの生成を有効または無効にします。 {$ R +}状態では、すべての配列式と文字列インデックス式が定義された範囲内にあると検証され、スカラー変数と部分範囲変数へのすべての代入が範囲内にあるかどうかがチェックされます。範囲チェックに失敗すると、ERangeError例外が発生します(または、例外処理が有効でない場合はプログラムが終了します)。

ここで理由は、スカラー値への代入であり、スカラー値には上の範囲を渡した値が渡されます。

docwiki Simple Typesも参照してください。単純型および部分範囲型の範囲検査エラーです。

例:すべてのプラットフォーム非依存の整数型のための$ R $及びQのすべての組み合わせの

{$R+} // Range check on 
var 
    w1,w2 : word; 
begin 
    w1 := High(word); 
    w1 := w1 + 10; // causes range-check error on assignment to w1 (upper range passed) 
    w2 := 0; 
    w2 := w2 - 10; // causes range-check error on assignment to w2 (lower range passed) 
end; 

要約試験:

  R+Q+ R+Q- R-Q+ 
ShortInt R  R  x 
SmallInt R  R  x 
Integer  O  x  O 
LongInt  O  x  O 
Int64  O  x  O 
Byte  R  R  x 
Word  R  R  x 
LongWord O  x  O 
Cardinal O  x  O 
UInt64  O  x  O 

R =レンジ誤差; O =オーバーフローエラー。 X =何も

とテストした32ビットモードでXE2と(擬似コード):

number := High(TNumber); 
number := number + 1; 
+1

@DavidHeffernanは、コードをテストしただけでレンジチェックエラーを生成します。の後ろに、スカラーと部分範囲変数へのすべての代入がチェックされていることを述べなければなりません。 –

+0

データ型が整数の場合、おそらくオーバーフローエラーとなるでしょう。 –

+0

@DavidHeffernan計算が 'Integer'型で実行されている場合、' i:= i + Int64(1); '*(テストされていない) 'i'が' MaxInt'の値を持つ 'Integer'であるときにレンジエラーが発生します。 – hvd

関連する問題