3

次のようなC#コードがあります。

uint a = 0x9E3779B9;
a += (uint)(url[k + 0] + (url[k + 1] << 8) + (url[k + 2] << 16) + (url[k + 3] << 24));

そのコードの後、a == 228 452 386

今、私はこのC#コードをPHPに変換しようとしていますが、PHPではその数は同じようにオーバーフローしません。

$a = 0x9E3779B9;
$a += ($url[$k+0] + ($url[$k+1] << 8) + ($url[$k+2] << 16) + ($url[$k+3] << 24));

そのコードの後、$ a == 4 523 419 682

どちらの場合も、「url」はASCII値の配列として扱われます。$ aが2行目の結果に追加されるまで、は同じ結果を返します。その時点で、C#のuintは約2億2800万にオーバーフローします。PHPは「賢く」なり、「正しい」答えを出します。

しかし、私はC#が与えるオーバーフローした答えが欲しいです。私は何をすべきか?

4

2 に答える 2

5

を実行した後、を追加し$a &= 0xFFFFFFFFて値を32ビット範囲に戻します+=

(参照:http ://www.ideone.com/6BR0U )

于 2010-11-07T20:01:28.047 に答える
0

しばらく経ち、実用的な回答がすでに提出されていますが、あなたが行っている開梱を実行するためのより簡単な方法を強調したいと思います。

$a = 0x9e3779b9;
$url = 'info';

$a = ($a + current(unpack('L', $url))) & 0xffffffff;

printf("%u\n", $a); // 228452387

unpack()バイナリからuint32(マシンバイトオーダー)への変換を実行するために使用しています。32ビットプラットフォームでは、最終結果がマイナスになる可能性がありprintf()ます。そのため、結果を適切にフォーマットするためにも使用しています。

于 2013-09-03T02:29:19.920 に答える