8

2 つの数値の合計/乗算が長整数の最大値を超えているかどうかを検出する際に問題があります。
コード例:

long a = 2 * Long.MAX_VALUE;
System.out.println("long.max * smth > long.max... or is it? a=" + a);

これは私-2に与えますが、私はそれがスローすることを期待していNumberFormatExceptionます...

これを機能させる簡単な方法はありますか?ネストされた IF ブロックで乗算またはループ内で加算を行うコードがいくつかあり、各 IF またはループ内にさらに IF を追加したくないためです。

編集:まあ、別の質問からのこの回答は、私が必要としているものに最も適しているようです : https://stackoverflow.com/a/9057367/540394
、そしてこの道は非常に短いので、私にとって大きなプラスです。これらのチェックを実行し、最小または最大の長さを返す 2 つの短い関数を記述します。

Edit2:上でリンクした回答に従って、 long を最小/最大値に制限する関数は次のとおりです。

/**
 * @param a : one of the two numbers added/multiplied
 * @param b : the other of the two numbers
 * @param c : the result of the addition/multiplication
 * @return the minimum or maximum value of a long integer if addition/multiplication of a and b is less than Long.MIN_VALUE or more than Long.MAX_VALUE
 */
public static long limitLong(long a, long b, long c)
{
    return (((a > 0) && (b > 0) && (c <= 0))
        ? Long.MAX_VALUE
        : (((a < 0) && (b < 0) && (c >= 0)) ? Long.MIN_VALUE : c));
}

これが間違っていると思うか教えてください。

4

3 に答える 3

5

結果が9兆兆未満になるかどうか確信が持てない場合は、私が使用するdoubleBigInteger、エラーが発生しても、何をすべきかを知る必要があるため、あまり役に立ちません。

long入力を検証して範囲内にあることを確認し、結果の範囲がこれを処理できるタイプを使用するよりも大きい場合は、最初にエラーが発生しない方がはるかに優れています。

BigIntegerを使用すると、次のことができます

BigInteger a = BigInteger.valueOf(2).multiply(BigInteger.valueOf(Long.MAX_VALUE));
long l = a.longValue();
if (a.compareTo(BigInteger.valueOf(l)) == 0) {
    // ok
} else {
    // error
}

ダブルであなたはすることができます

double d = 2.0 * Long.MAX_VALUE;
long l = (long) Math.max(Long.MIN_VALUE, Math.min(Long.MAX_VALUE, d));
// or as a helper method.
long l = boundedCast(d);

注:doublelongの代わりに使用すると、精度がいくらか失われる可能性があります。

そもそもエラーブロックの必要性を避けたいと思います。

于 2012-09-10T08:46:24.287 に答える
5

long の最大値を超えても例外はスローされず、代わりに元に戻ります。これを行う場合:

Long.MAX_VALUE + 1

結果は次と同等であることがわかりますLong.MIN_VALUE

例外をスローする場合は、最大値に達したかどうかを確認して例外をスローします

[編集]

Guava Library を使用して、2 つの long を合計するときにオーバーフローがあるかどうかを確認することもできます。

long c = LongMath.checkedAdd(a, b);

これは、オーバーフローが発生したときに例外をスローします。

javadocはここにあります。

于 2012-09-10T08:50:03.553 に答える
0

Long値を超えMAX_VALUEても例外はスローされません。このような状況を手動で確認して処理する必要があります。

ただし、@PeterLawrey が提案したように、 and の使用を検討する必要がdoubleありBigIntegerます。

于 2012-09-10T08:53:15.130 に答える