web-dev-qa-db-ja.com

64ビットコンパイラでintが通常32ビットであるのはなぜですか?

intが64ビットコンパイラで通常32ビットであるのはなぜですか?私がプログラミングを始めたとき、intは通常、基本的なアーキテクチャと同じ幅であると教えられてきました。そして、これも理にかなっていることに同意します。未指定の幅の整数は、基盤となるプラットフォームと同じ幅にするのが理にかなっていると思います(intのこのような小さな範囲でかろうじて適用されます)。

後で、intがほとんどの64ビットプラットフォームで通常32ビットであることを学びました。だから何故かしら。データを格納するために、明示的に指定されたデータ型の幅を好むので、これはintの一般的な使用法を残しますが、少なくとも私のシステムでは32と64ビット整数。そのため、バイナリメモリのフットプリントが残りますが、それほどではありませんが、わずかに削減されます...

33
user2341104

実装者側の悪い選択?

真剣に、標準によれば、「プレーンなintは、実行環境のアーキテクチャによって提案された自然なサイズを持っています」。これは、64ビットマシン上の64ビットintを意味します。他のものは不適合であると簡単に主張することができます。しかし、実際には、問題はより複雑です:32ビットintから64ビットintに切り替えるとnot大部分のプログラムが大きなデータセットやその他のものを処理できるようになります( 16ビットから32ビットへの切り替え);ほとんどのプログラムは、おそらく他の考慮事項によって制約されています。そして、それはデータセットのサイズを増やし、それによって局所性を減らし、プログラムを遅くします。

最後に(そしておそらく最も重要なこととして)、intが64ビットの場合、shortは16ビットまたは32ビットのいずれかである必要があり、他のものを指定する方法はありません( <stdint.h>のtypedef、およびこれらは非常に例外的な状況でのみ使用されることを意図しています)これが大きな動機だったと思います。

12
James Kanze

歴史、トレードオフ、および決定については、The Open Group http://www.unix.org/whitepapers/64bit.html で説明されています。さまざまなデータモデル、それらの長所と短所、および64ビットコンピューティングに対応するためにUnix仕様に加えられた変更について説明します。

7
Phil P

intsは、ほとんどの主要なアーキテクチャで32ビットであったため、64ビットに変更すると、解決するよりも多くの問題が発生する可能性があります。

5
doron

多くのソフトウェアが64ビット整数を持つことには利点がないからです。

64ビット整数を使用して32ビット整数で計算できるものを計算し(多くの目的で、最大40億(または+/- 2ビロン)の値で十分です)、それらを大きくしても何の助けにもなりません。

ただし、大きな整数を使用すると、プロセッサのキャッシュに収まるサイズの整数の「もの」の数にマイナスの影響があります。したがって、それらを大きくすると、多数の整数(配列など)を含む計算に時間がかかるためです。

intは機械語の自然なサイズであり、WordはC++標準で規定されているものではありません。ほとんどのマシンが16ビットまたは32ビットである時代には、16ビットまたは32ビットにするのが理にかなっています。これは、これらのマシンにとって非常に効率的なサイズだからです。 64ビットマシンに関しては、それはもはや「助け」にはなりません。したがって、32ビットintを使用するほうが理にかなっています。

編集:興味深いことに、Microsoftが64ビットに移行したとき、longが32ビット値であることに依存している多くのものが壊れてしまうため、longを64ビットにすることさえしませんでした。 (さらに重要なことに、APIでlongが32ビット値であることに依存していたことがたくさんありました。クライアントソフトウェアはintlongを使用することがあります。そして彼らはそれが壊れることを望まなかった)。

2
Mats Petersson

主な理由は、下位互換性です。さらに、すでに64ビット整数型longがあり、フロート型floatおよびdoubleについても同様です。アーキテクチャごとにこれらの基本タイプのサイズを変更すると、複雑さが増すだけです。さらに、32ビット整数は、範囲の点で多くのニーズに対応します。

1
fatihk

これは この質問 への回答として最初に書いたものです。いくつか変更しましたが、ほとんど同じです。

はじめに、 C++ドラフト が示すように、32ビットより広いプレーン整数を使用できます。

注:プレーンなintは実行環境のアーキテクチャによって提案された自然なサイズ;を持つことを目的としています。その他の符号付き整数型は、特別なニーズを満たすために提供されています。 — endend

強調鉱山

これは一見すると、私の64ビットアーキテクチャ(および他のすべてのアーキテクチャ)では、プレーンなintは64ビットサイズである必要があると言っているように見えます。それはアーキテクチャによって提案されたサイズですよね?ただし、64ビットアーキテクチャでもnaturalサイズis32ビットであることを主張する必要があります。仕様の引用は主に、16ビットのプレーン整数が必要な場合に使用されます。これは、仕様で許可されている最小サイズです。

最大の要因は慣習であり、32ビットの単純なintを備えた32ビットアーキテクチャから64ビットアーキテクチャにそのソースを適応させることは、設計者とそのユーザーの両方にとって、2つの異なる方法で32ビットを維持する方が簡単です。

1つ目は、システム間の差異が少ないほど、誰にとっても簡単になるということです。システム間の不一致は、ほとんどのプログラマにとって頭痛の種でした。それらは、システム間でコードを実行することを困難にするだけのものです。 32ビットと64ビットの同じディストリビューションのコンピューター間では実行できない比較的まれなケースに追加されます。ただし、John Kugelmanが指摘したように、アーキテクチャは16ビットから32ビットの単純な整数に移行しました。そのため、面倒な作業を繰り返す必要があり、今日も次の点につながります。

より重要なコンポーネントは、整数サイズまたは新しいタイプで必要となるギャップです。 sizeof(short) <= sizeof(int) <= sizeof(long) <= sizeof(long long)は実際の仕様にあるため、プレーンなintが64ビットに移動されると、ギャップが強制されます。 longのシフトから始まります。単純なintが64ビットに調整されている場合、sizeof(int) <= sizeof(long)longを少なくとも64ビットに強制するという制約があり、そこからサイズに本質的なギャップがあります。 longまたは通常のintは通常32ビット整数として使用され、現在はどちらも使用できないため、shortのデータ型はもう1つしかありません。 shortの最小サイズは16ビットであるため、そのサイズを単に破棄すると32ビットになり、理論的にはそのギャップを埋めることができますが、shortはスペースを最適化してはそのままにしておく必要があり、小さい16ビット整数のareユースケースもあります。サイズをどのように配置しても、幅が失われるため、intの使用例はまったく利用できません。幅が大きくても、必ずしも優れているとは限りません。

これは、仕様を変更する必要があることを意味しますが、設計者が不正になったとしても、損傷するか、変更によって陳腐化する可能性が高くなります。長期的なシステムの設計者は、システム内の独自のコード、依存関係、実行したいユーザーのコードの両方を絡み合わせたコードのベース全体で処理する必要があり、影響を考慮せずにそうするために膨大な量の作業を行うことは単純に賢明ではありません。 。

補足として、アプリケーションが32ビットを超える整数と互換性がない場合は、static_assert(sizeof(int) * CHAR_BIT <= 32, "Int wider than 32 bits!");を使用できます。ただし、仕様willが変更され、64ビットのプレーンな整数が実装されることを知っている場合は、将来の証拠になりたい場合は、静的アサートを行わないでください。

1
David Archibald

まだ誰もこれを指摘していないので。

int-32767から32767(2^16)の間であることが保証されています。これは規格で必要とされています。すべてのプラットフォームで64ビットの数値をサポートする場合は、(-9223372036854775807〜9223372036854775807)をサポートする正しいタイプlong longを使用することをお勧めします。

intは、規格で必要な最小範囲を提供する限り、何でもかまいません。

0
andre

C++標準では、int型に使用するメモリの量は規定されておらず、少なくともint型に使用するメモリの量が示されています。 32ビットポインター変数の多くのプログラミング環境では、 "int"と "long"はすべて32ビット長です。

0
eispeed