2の補数は、コンピュータ上で符号付き(正、負、ゼロ)整数を表す最も一般的な方法であり、 [ 1 ]より一般的には固定小数点バイナリ値を表します。1の補数や符号と絶対値システムと同様に、2の補数では最上位ビットを符号として使用して正(0)または負(1)の数を示し、非負の数は符号なし表現で表されます(6は0110、0は0000)。ただし、2の補数では、負の数は絶対値のビット補数を取って1を加えることで表されます(-6は1010)。表現のビット数は、負または正の数のすべての追加の上位ビットをそれぞれ1または0で埋めることで増加し、追加の先頭の1または0を削除することで減少します。
1の補数方式とは異なり、2の補数方式ではゼロの表現は1つしかなく、負の数を1つ追加で表現する余地があります(4ビット数の範囲は-8から+7です)。さらに、同じ算術実装を符号付き整数と符号なし整数の両方で使用でき[ 2 ] 、正の数とその負の数の表現の合計が0(キャリービットがセットされている場合)であるため、整数オーバーフローの状況 のみが異なります。
与えられた負の数を2進数で表した2の補数表現を得る手順は以下のとおりです。
例えば、10進数の-6を6から2進数で計算するには、次のようにします。
1010 の値が実際に−6であることを確認するには、位の値を足し合わせますが、最終的な計算から符号の値を引きます。最上位の値は符号の値であるため、正しい結果を得るにはそれを引き下げる必要があります。1010 = − ( 1 × 2 3 ) + ( 0 × 2 2 ) + ( 1 ×2 1 ) + ( 0 ×2 0 ) = 1 ×−8 + 0 + 1 ×2 + 0 = −6。
ステップ2とステップ3を組み合わせることで、加法逆元を計算する有効な方法となる。任意の(正または負の)整数入力と出力の両方が2の補数である。引き算を使う2の補数表現における整数の減算については、以下を参照してください。

2の補数は、基数補数の例です。名前の「2」は、2N(「2のN乗」)という数を指し、NビットシステムではこのN乗を基準として補数が計算されます(この項で正確に「2」が生成される唯一のケースはN =1の場合、つまり1ビットシステムの場合ですが、1ビットシステムでは符号とゼロの両方を表現できません)。したがって、 Nビット数の2の補数の正確な定義は、その数を2Nで補ったものです。
2 Nに関してある数の補数であることの定義特性は、この数と元の数を足し合わせると2 Nになるということです。たとえば、3 ビットまでの数値でバイナリを使用する場合 ( N = 3で2 N = 2 3 = 8 = 1000 2、ここで「2」はバイナリ表現を示します)、数 3 ( 011 2 ) の 2 の補数は 5 ( 101 2 ) です。これは、元の数に足し合わせると2 3 = 1000 2 = 011 2 + 101 2になるからです。この対応関係を負の数の表現に用いる場合、実際には、10進数の類推と、0から7までの8つの非負の数のみを許容する数空間を用いて、数空間を2つのセットに分割することを意味します。最初の4つの数0 1 2 3はそのままですが、残りの4つは負の数をエンコードし、その増加順序を維持します。つまり、4は-4、5は-3、6は-2、7は-1をエンコードします。ただし、2進数表現には、最上位ビットがグループ(および符号)も示すという追加の有用性があります。最初の非負のグループの場合は0、2番目の負のグループの場合は1です。右側の表はこの特性を示しています。
正の数のバイナリ 2 の補数を計算するということは、基本的にその数を2 Nから減算することを意味します。しかし、3 ビットの例と 4 ビットの1000 2 ( 2 3 ) でわかるように、数2 N はNビット空間のすぐ外側にあるため、N ビットに制限されたシステムではそれ自体は表現できません(それでもこの数は、 Nビット システムでの「2 の補数」の基準点です)。このため、最大でNビットのシステムでは、減算を 2 つの操作に分割する必要があります。まず、Nビット システムでの最大値、つまり2 N −1 (バイナリではこの項は実際には「すべて 1」で構成される単純な数であり、その減算は、ビットごとの NOT 演算としても知られる数のすべてのビットを反転するだけで実行できます) から減算し、次に 1 を加えます。偶然にも、1を加える前のその中間数は、コンピュータサイエンスにおいて符号付き数の表現方法として用いられており、1の補数と呼ばれています(このような数を元の数と足すと「すべて1」になることから、このように名付けられました)。
符号付き数を表現する他のシステム(例えば、1の補数)と比較すると、2の補数には、加算、減算、乗算といった基本的な算術演算が符号なし2進数の場合と同じであるという利点があります(入力が出力と同じビット数で表現され、そのビット数を超えるオーバーフローが結果から破棄される限り)。この特性により、特に高精度の算術演算において、システムの実装が容易になります。さらに、1の補数システムとは異なり、2の補数には負のゼロの表現がないため、それに伴う困難もありません。それ以外では、どちらの方式も、整数の符号を2進数表現の補数を取ることで反転できるという望ましい特性を備えていますが、2の補数には例外があります。それは、表で確認できる最小の負の数です。[ 4 ]
補数法は、 10進加算機や機械式計算機で減算を行うために長年使用されてきた。ジョン・フォン・ノイマンは、電子式プログラム内蔵型デジタルコンピュータのEDVAC提案に関する1945年の報告書の第一草稿で、2の補数による2進数表現の使用を提案した。 [ 5 ]第一草稿に触発された1949年のEDSACは、負の2進整数の2の補数表現を使用した。
CDC 6600、LINC、PDP-1、UNIVAC 1107など、初期のコンピュータの多くは1の補数表記を使用しており、UNIVAC 1107の後継機種であるUNIVAC 1100/2200シリーズも引き続き使用していました。(後の18ビットDECマシンは、ADD命令による1の補数加算とTAD命令による2の補数演算の両方をサポートしていました。)IBM 700/7000シリーズの科学計算機は、インデックスレジスタを除いて符号/絶対値表記を使用しており、インデックスレジスタは2の補数です。負の値を2の補数形式で格納する初期の商用コンピュータには、English Electric DEUCE(1955年)やDigital Equipment Corporation PDP-5(1963年)およびPDP-6(1964年)などがあります。 (PDP-5 および PDP-8 ファミリーのコンピュータは、1 の補数 ADD 命令がなかったにもかかわらず、2 の補数加算のアセンブラ ニーモニック TAD を引き続き使用しました。)1964 年に、当時コンピュータ業界で支配的な地位にあったIBMが発表したSystem/360は、2 の補数をコンピュータ業界で最も広く使用されているバイナリ表現にしました。最初のミニコンピュータである 1965 年に発表されたPDP-8 は、 1969 年のData General Nova、1970 年のPDP-11、およびそれ以降のほとんどすべてのミニコンピュータとマイクロコンピュータと同様に、2 の補数演算を使用しています。
2の補数表現は、正の数と負の数を二進数で表現するシステムです。各ビットの重みは2のべき乗ですが、最上位ビットの重みは対応する2のべき乗の負の値になります。
Nビット整数の値w 次の式で与えられます。
最上位ビットは数値の符号を決定し、符号ビットと呼ばれることもあります。符号と絶対値表現とは異なり、符号ビットには上記のように−(2 N − 1 )の重みがあります。Nビットを使用すると、 −(2 N − 1 )から2 N − 1 − 1までのすべての整数を表現できます。
2の補数表記では、非負の数は通常の2進数表現で表されます。この場合、最上位ビットは0です。ただし、表現できる数値の範囲は、符号なし2進数とは異なります。たとえば、8ビットの符号なし数は、0から255(11111111)までの値を表すことができます。しかし、2の補数8ビット数は、0から127(01111111)までの非負の整数しか表現できません。これは、最上位ビットが「1」である残りのビットの組み合わせが、-1から-128までの負の整数を表すためです。
2の補数演算は加法逆演算なので、負の数は絶対値の2の補数で表されます。
負の2進数の2の補数を求めるには、ビットごとのNOT演算を使用してすべてのビットを反転(「反転」)します。次に、結果の値に1を加算します。このとき、0の2の補数を取る際に発生するオーバーフローは無視されます。
例えば、1バイト(=8ビット)を使用すると、10進数5は次のように表されます。
最上位ビット(この場合は左端のビット)は0なので、このパターンは非負の値を表します。2の補数表記で-5に変換するには、まずすべてのビットを反転させます。つまり、0は1になり、1は0になります。
この時点では、表現は10進数値-5の1の補数です。2の補数を得るには、結果に1を加えると次のようになります。
結果として得られるのは、10進数の-5を2の補数で表した符号付き2進数です。最上位ビットは1であり、これは表される値が負であることを示しています。
あるいは、正の2進数を反転した後に1を加える代わりに、反転する前にその数から1を引くこともできます。この2つの方法は簡単に同等であることが示せます。等しい反転と 1 の合計はこれは、2 の補数に等しい。予想通り。等しい前の式と同一です。本質的に、反転演算に内在する減算は、-1 を加えたものを変更します。反転前に+1を加算し、反転後に+1を加算します。この代替の減算と反転アルゴリズムを使用して2の補数を生成する方法は、コンピュータプログラミングやハードウェア設計において有利になる場合があります。たとえば、1の減算を以前の操作に組み込むことで無料で取得できる場合などです。[ 6 ]
負の数の2の補数は、最も負の数の特殊な場合を除いて、対応する正の値になります。たとえば、−5(上記)のビットを反転すると次のようになります。
そして、1を加えると最終値が得られます。
表現可能な最大の負の数(例えば、最上位ビットが1で、他のすべてのビットが0の場合)の2の補数は、それ自身になります。したがって、2の補数では負の数を表現できない「余分な」負の数があります。詳しくは、下記の「 最大の負の数」の項を参照してください。
最も負の数の場合、それは 2 つの特別なケースのうちの 1 つです。もう 1 つの特別なケースはゼロで、その 2 の補数はゼロです。反転するとすべて 1 になり、1 を加えると 1 がゼロに戻ります (オーバーフローは無視されるため)。数学的には、符号付き整数の 2 の補数システム (各数の負をその 2 の補数として表す) では、これは明らかに正しいです。0 の負は実際には 0 (このゼロの場合も、2の補数の定義から考えても理にかなっています。その定義によれば、ゼロの2の補数は次のようになります。しかし、ビット、すべての値はモジュロで取得されます、 そしてモジュール言い換えれば、0の2の補数はビットは(定義上)1ビットの後にゼロになるが、1は切り捨てられ、0が残る。[ 7 ]
要約すると、正の数、負の数、ゼロのいずれであっても、任意の数の2の補数は同じ方法で計算できます。符号付き整数の2の補数表現では、任意の整数の2の補数は、与えられたビット数で表現できる最大の負の整数を除いて、その整数の-1倍に等しくなります。つまり整数2の補数はそれ自身である(それでも負の値)。
ある数とその1の補数の和は、すべてのビットが1であるNビットワードであり、これは(符号なし2進数として読むと)2N - 1です。次に、ある数にその2の補数を加えると、下位Nビットが0になり、キャリービットが1になります。後者の重みは(符号なし2進数として読むと)2Nです。したがって、符号なし2進数演算では、正の数xの2の補数の負の数x *の値は、x * = 2N - xという等式を満たします。[ a ]
例えば、−5 の 4 ビット表現を求めるには (添え字は表現の基数を表します) :
したがって、N = 4の場合:
計算はすべて10進数で行い、最後に2進数に変換すればよい。
バイナリ数を手動で2の補数に変換する簡単な方法は、最下位ビット(LSB)から始めて、すべてのゼロをコピーし、LSBから最上位ビット(MSB)に向かって最初の 1に到達するまで作業を進め、その 1をコピーして、残りのすべてのビットを反転することです(元の数が符号と絶対値で表現されていた場合は、MSBを1のままにします)。この簡単な方法を使用すると、1の補数を最初に作成することなく、数を2の補数に変換できます。たとえば、2の補数表現では、「0011 1100」の否定は「1100 0 100」になります。ここで、下線が引かれた数字はコピー操作によって変更されず(残りの数字は反転されます)。
コンピュータ回路においては、この方法は「補数化して1を加える」方法よりも高速ではありません。どちらの方法も、論理変化を伝播させながら右から左へ順次処理する必要があるためです。補数化して1を加える方法は、標準的なキャリー先読み加算器回路によって高速化できます。同様に、LSBからMSBへ進む方法も、同様の論理変換によって高速化できます。
特定のビット数を持つ2の補数表現の数を、より多くのビットを持つ数に変換する場合(例えば、1バイト変数から2バイト変数にコピーする場合)、最上位ビットは追加されるすべてのビットに繰り返される必要があります。一部のプロセッサではこれを単一の命令で実行しますが、他のプロセッサでは、条件分岐の後に、関連するビットまたはバイトを設定するコードを実行する必要があります。
同様に、数値を右シフトする場合、符号情報を含む最上位ビットは保持されなければなりません。しかし、左シフトの場合は、1ビットがシフトアウトされます。これらの規則は、左シフトは数値を2倍し、右シフトは数値を2で割るという共通の意味を維持します。ただし、最上位ビットが0から1(またはその逆)に変化した場合、その値が符号付き整数を表す場合はオーバーフローが発生したと言われます。
乗算アルゴリズムによっては、シフトと精度倍増の両方が重要となる。加算や減算とは異なり、符号付き数と符号なし数では、幅の拡張と右シフトの処理方法が異なる。
例外は1つだけですが、2の補数表現の任意の数値から始めて、すべてのビットを反転して1を加えると、その数値の負の数の2の補数表現が得られます。正の 12は負の12に 、正の 5は負の 5に、0は0(+オーバーフロー)になります。
範囲内の最小値の2の補数(否定)を取っても、数値を否定するという望ましい効果は得られません。たとえば、8ビットシステムで-128の2の補数は、右の表に示すように-128 です。 -128を否定すると+128になるはずですが、 8ビットの2の補数システムでは+128を表す方法がないため、実際には否定を表すことはできません。2の補数が同じ数値であることは、最上位ビットへの桁上がりはあったものの、最上位ビットから桁上がりがなかったため、オーバーフロー状態として検出されます。
ゼロ以外の数が自身の否定と等しくなるのは、ゼロが自身の否定であり、数の総数が偶数であるという事実によって必然的に起こります。証明:ゼロ以外の数は2^n − 1 個(奇数)あります。否定によってゼロ以外の数はサイズ 2 の集合に分割されますが、そうするとゼロ以外の数の集合の濃度が偶数になってしまいます。したがって、少なくとも 1 つの集合のサイズは 1 であり、つまり、ゼロ以外の数は自身の否定です。
最も負の数が存在すると、結果の符号が予期しないものになったり、予期しないオーバーフロー例外が発生したり、まったく奇妙な動作を引き起こしたりするなど、予期しないプログラミングバグが発生する可能性があります。たとえば、
CおよびC++プログラミング言語では、上記の動作は未定義であり、奇妙な結果を返す可能性があるだけでなく、コンパイラはプログラマが未定義の数値演算が発生しないように保証したと仮定し、その仮定から推論を行うことができます。[ 10 ]これにより多くの最適化が可能になりますが、これらの未定義の計算を含むプログラムでは多くの奇妙なバグが発生します。
2の 補数におけるこの最も負の数は、唯一の例外であるため、「奇妙な数」と呼ばれることがあります。[ 11 ] [ 12 ] この数は例外ではありますが、通常の2の補数システムでは有効な数です 。すべての算術演算は、オペランドとしても(オーバーフローがない限り)結果としても機能します。
すべての可能なNビット値の集合が与えられた場合、下位 (バイナリ値による) 半分を 0 から(2 N − 1 − 1)までの整数に、上位半分を−2 N − 1 から −1 までの整数に割り当てることができます。上位半分 (これもバイナリ値による) は、−2 N − 1から−1 までの負の整数を表すために使用できます。なぜなら、2 Nを法とする加算では、これらの負の整数と同じように動作するからです。つまり、i + j mod 2 N = i + ( j + 2 N ) mod 2 Nであるため、集合{ j + k 2 N | kは整数 } の任意の 値をjの代わりに使用できます。[ 13 ]
例えば、8ビットの場合、符号なしバイトは0から255までです。上位半分(128から255)から256を引くと、符号付きバイトは-128から-1までになります。
2の補数との関係は、256 = 255 + 1であり、(255 − x )がxの1 の補数であることに注目することで理解できます。
例えば、8 ビットの数値は、−128から127までのすべての整数を表すことができます。なぜなら、(2 8 − 1 = 128)だからです。−95を256で割った余りは161に等しくなります。
1111 1111 255。 − 0101 1111 − 95。 =========== ===== 1010 0000 (1の補数) 160。 + 1 + 1 =========== ===== 1010 0001 (2の補数) 161。
基本的に、このシステムは負の整数を逆方向に数えてラップアラウンドすることで表現します。正の数と負の数の境界は任意ですが、慣例としてすべての負の数は最左ビット(最上位ビット)が1になります。したがって、最も正の4ビット数は0111 (7.)であり、最も負の数は1000(-8.)です。最左ビットを符号ビットとして使用するため、最も負の数(|-8.| = 8.)の絶対値は大きすぎて表現できません。2の補数の数を否定するのは簡単です。すべてのビットを反転し、結果に1を加えます。たとえば、1111を否定すると、0000 + 1 = 1になります。したがって、2進数の1111は10進数で-1を表す必要があります。[ 14 ]
このシステムは、コンピュータハードウェア上での算術演算の実装を簡素化するのに役立ちます。0011 (3.) と 1111 (−1.) を加算すると、最初は誤った答えである 10010 が得られるように見えます。しかし、ハードウェアは最左端のビットを無視することで、正しい答えである 0010 (2.) を得ることができます。0100 と 0100 を加算するなどの演算を検出するために、オーバーフローチェックは依然として必要です。
したがって、このシステムでは、減算回路や符号判定回路を用いることなく、負のオペランドを加算することができます。さらに、この加算回路は、数値の2の補数を取ることで減算も実行できます(下記参照)。これには、追加のサイクルまたは独自の加算回路のみが必要です。この処理を実行するために、回路は単に最左端のビットが1であるかのように動作します。
2の補数表現の加算では、オペランドの符号が反対であっても特別な処理は必要ありません。結果の符号は自動的に決定されます。例えば、15と-5を加算する場合:
0000 1111 (15) + 1111 1011 (−5) =========== 0000 1010 (10)
または、5 − 15 = 5 + (−15) の計算式は次のとおりです。
0000 0101 ( 5) + 1111 0001 (−15) =========== 1111 0110 (−10)
このプロセスは精度を 8 ビットに制限することに依存しており、(存在しない) 9 番目の最上位ビットへの桁上がりは無視され、結果として算術的に正しい結果 10 10になります。
桁上がり行の最後の 2 ビット(右から左に読む) には、重要な情報が含まれています。それは、計算結果が算術オーバーフロー、つまりバイナリシステムで表現するには大きすぎる数 (この場合は 8 ビットより大きい数) になったかどうかです。オーバーフロー状態は、この最後の 2 ビットが異なる場合に発生します。前述のとおり、数値の符号は結果の最上位ビット (MSB) にエンコードされます。
言い換えれば、左端の2つのキャリービット(これらの例では最上段の一番左にあるビット)が両方とも1または両方とも0であれば、結果は有効です。左端の2つのキャリービットが「1 0」または「0 1」であれば、符号オーバーフローが発生しています。便利なことに、これら2つのビットに対してXOR演算を行うことで、オーバーフロー状態が存在するかどうかを迅速に判断できます。例として、7と3の符号付き4ビット加算を考えてみましょう。
0111(キャリー) 0111 (7) + 0011 (3) ====== 1010 (−6) 無効です!
この場合、最上位ビット(MSB)の桁上げビットは「01」であり、これは2の補数加算でオーバーフローが発生したことを意味します。つまり、1010 2 = 10 10は許容範囲である-8から7の範囲外です。符号なし整数として扱えば、結果は正しくなります。
一般に、任意のNビットの数値 2 つを、まず両方を N + 1 ビットに符号拡張してから上記のように加算することで、オーバーフローなしで加算できます。N + 1 ビットの結果は、考えられるすべての和を表すのに十分な大きさであるため (N = 5 の場合、 2の 補数は-16から15 の範囲の値を表現できます)、オーバーフローは決して発生しません。必要に応じて、破棄するビットが保持する結果ビットの適切な符号拡張である場合に限り、値を保持したまま結果をNビットに「切り捨て」ることができます。これは、オーバーフローを検出する別の方法であり、キャリー ビットを比較する方法と同等ですが、加算の内部にアクセスする必要がないため、状況によっては実装が容易になる場合があります。
コンピュータは通常、減算を実行するために補数法を使用します。減算に補数を使用することは、負の数を表現する際に補数を使用することと密接に関連しています。これは、補数と減算の組み合わせによって、オペランドと結果のすべての符号を表現できるためです。直接減算は、2の補数表現の数でも機能します。加算と同様に、2の補数を使用する利点は、加算または減算が必要かどうかを判断するためにオペランドの符号を調べる必要がなくなることです。たとえば、15から-5を引くことは、実際には15に5を加えることですが、これは2の補数表現によって隠されています。
11110 000(借用) 0000 1111 (15) − 1111 1011 (−5) =========== 0001 0100 (20)
オーバーフローは加算の場合と同様に、借りた桁の左端(最上位)の2ビットを調べることで検出されます。これらのビットが異なれば、オーバーフローが発生したことになります。
別の例として、結果が負になる減算演算があります。15 − 35 = −20:
11100 000(借入) 0000 1111 (15) − 0010 0011 (35) =========== 1110 1100 (−20)
加算の場合と同様に、減算におけるオーバーフローは、まず両方の入力に1ビットの符号拡張を行うことで回避(または演算後に検出)できます。
2つのNビット数の積は、すべての可能な値を格納するために2Nビットを必要とする。[ 15 ]
2 の補数を使用して 2 つのオペランドの精度を乗算前に 2 倍にすると、直接乗算 (その精度を超える余分なビットを破棄する) で正しい結果が得られます。[ 16 ]例えば、6 × (−5) = −30を考えてみましょう。まず、精度を 4 ビットから 8 ビットに拡張します。次に、数値を乗算し、8 ビット目を超えるビットを破棄します (「 x 」で示されているように)。
00000110 (6) * 11111011 (−5) ============ 110 1100 00000 110000 1100000 11000000 x10000000 + xx00000000 ============ xx11100010
これは非常に非効率的です。事前に精度を2倍にすると、すべての加算が倍精度で行われなければならず、コンピュータに実際に実装されているより効率的なアルゴリズムよりも少なくとも2倍の部分積が必要になります。一部の乗算アルゴリズムは2の補数用に設計されており、特にブースの乗算アルゴリズムが挙げられます。符号と絶対値を持つ数を乗算する方法は、適応させなければ2の補数では機能しません。被乗数(積を形成するために繰り返し加算される数)が負の場合、通常は問題はありません。問題は、乗数が負の場合に積の最初のビットを正しく設定することです。2の補数を扱うようにアルゴリズムを適応させる一般的な方法は2つあります。
2番目の方法の例として、一般的な加算シフト乗算アルゴリズムを考えてみましょう。鉛筆と紙で行うように部分積を左にシフトする代わりに、累積された積は右にシフトされ、最終的に積の最下位半分を格納する2番目のレジスタに格納されます。最下位ビットは計算後に変更されないため、加算は単精度で行え、最終的に積の最上位半分を格納するレジスタに累積されます。次の例では、再び6と-5を乗算しますが、2つのレジスタと拡張符号ビットは「|」で区切られています。
0 0110 (6) (拡張符号ビット付き被乗数) × 1011 (−5) (乗数) =|====|==== 0|0110|0000(最初の部分積(最右端のビットは1)) 0|0011|0000(右シフト、拡張符号ビットを保持) 0|1001|0000(2番目の部分積を加算(次のビットは1)) 0|0100|1000(右シフト、拡張符号ビットを保持) 0|0100|1000(3番目の部分積を追加:0なので変化なし) 0|0010|0100(右シフト、拡張符号ビットを保持) 1|1100|0100(符号ビットからの積なので、最後の部分積を減算します) 1|1110|0010(右シフト、拡張符号ビットを保持) |1110|0010(拡張符号ビットを破棄し、最終的な答えである-30を得る)
比較は、多くの場合、ダミー減算によって実装されます。この場合、コンピュータの状態レジスタのフラグがチェックされますが、実際の結果は無視されます。ゼロフラグは、比較された2つの値が等しいかどうかを示します。符号フラグとオーバーフローフラグの排他的論理和が1の場合、減算結果は0未満であり、それ以外の場合は0以上です。これらのチェックは、コンピュータでは条件分岐命令によって実装されることがよくあります。
符号なし2進数は、単純な辞書式順序で並べることができ、ビット値0はビット値1より小さいと定義されます。2の補数表現の場合、最上位ビットの意味は逆になります(つまり、1は0より小さい)。
以下のアルゴリズム(nビット2の補数アーキテクチャの場合)は、A < B の場合は結果レジスタRを-1に、A > B の場合は+1に、AとBが等しい場合は0に設定します。
// 符号ビットの逆比較A ( n - 1 ) = 0かつB ( n - 1 ) = 1の場合、+ 1を返す。そうでなければ、 A ( n - 1 ) = 1かつB ( n - 1 ) = 0の場合、-1 を返す。//残りのビットの比較for i := n - 2 downto 0 do begin if A ( i ) = 0 and B ( i ) = 1 then return - 1 else if A ( i ) = 1 and B ( i ) = 0 then return + 1 end end return 01972年にMIT AIラボが発表した古典的なHAKMEMの中で、ビル・ゴスパーは、機械の内部表現が2の補数であるかどうかは、2の連続するべき乗を合計することで判断できると指摘した。彼は空想的に、これを代数的に行った結果、「代数は2の補数である機械(宇宙)上で実行されている」ことを示していると指摘した。[ 18 ]
ゴスパーの最終的な結論は必ずしも真剣に受け止められるべきものではなく、数学のジョークに似ています。重要なステップは「...110 = ...111 − 1」、つまり「2 X = X − 1」であり、したがってX = ...111 = −1 です。これは、無限の 1 の列を数とみなす方法を前提としており、初等算術 の有限位取りの概念の拡張が必要です。これは、すべての整数の 2 の補数表記の一部として、典型的な2 進数として、または実数の発散系列1 + 2 + 4 + 8 + ⋯に対して定義された一般化された和の 1 つとして意味があります。[ 19 ]無限 (2 の正のべき乗まで拡張) ビット列で動作するように理想化されたデジタル算術回路は、2 の補数表現と互換性のある 2 進加算と乗算を生成します。[ 20 ] 2進メトリックにおけるバイナリ算術演算およびビット演算の連続性は、暗号化にもいくらか利用されている。[ 21 ]
.0101 のような小数部を持つ数値を変換するには、通常の変換と同様に、右から左へ 1 を小数に変換する必要があります。この例では、0101 は 10 進数で 5 に相当します。浮動小数点以下の各桁は、分母が 2 の倍数である分数を表します。したがって、最初の桁は 1/2、2 番目の桁は 1/4 などとなります。上記のように既に小数値を計算しているため、LSB (LSB = 右から) の分母のみを使用します。この変換の最終結果は 5/16 です。
例えば、この方法を実行するために浮動小数点値 0.0110 を使用する場合、右端の 0 は考慮しない必要があります。したがって、0110 の小数値を計算する代わりに、011 を計算します。これは小数で 3 です (末尾の 0 を残しておくと、結果は 6 となり、分母 2 4 = 16 とすると 3/8 になります)。分母は 8 なので、最終結果は 3/8 となります。