4

「int」フレーバー(unsigned int、long int、long long int)に関して次の疑問があります。

32ビットシステムと64ビットシステムでintとそのフレーバー(たとえばlong int)の間でいくつかの操作(*、/、+、-)を実行すると、「int」に対して暗黙の型キャストが発生します。

例えば ​​:-

int x; long long int y = 2000;

x = y; (上位が下位に割り当てられ、1つのデータが切り捨てられる可能性があります)コンパイラがこれについて警告することを期待していますが、そのような警告は表示されません。これは、ここで「x」に対して暗黙の型キャストが発生したためですか。-Wallオプションを指定してgccを使用しています。動作は32ビットと64ビットで変更されますか。

ありがとうArpit

4

5 に答える 5

7

-Wall考えられるすべての警告がアクティブになるわけではありません。-Wextra他の警告を有効にします。とにかく、あなたがすることは完全に「合法的な」操作であり、コンパイラはコンパイル時に「切り捨てられる」可能性のあるデータの値を常に知ることができないので、警告しなくても大丈夫です。プログラマはすでに知っているはずです。 「大きい」整数が「小さい」整数に収まらないという事実については、通常はプログラマー次第です。プログラムがこれを認識せずに作成されていると思われる場合は、を追加して-Wconversionください。

于 2010-07-13T05:55:12.660 に答える
3

明示的な型キャスト演算子を使用しないキャストは、Cでは完全に有効ですが、未定義の動作をする可能性があります。あなたの場合、int x;は署名されているので、の範囲外の値を格納しようとするとint、プログラムの動作は未定義になります。一方、動作が明確に定義されているxと宣言された場合。unsigned x;キャストはリダクションモジュロを介して行われUINT_MAX+1ます。

算術に関しては、異なるタイプの整数間で算術を実行すると、算術の前に「小さい」タイプが「大きい」タイプにプロモートされます。もちろん、結果に影響がない場合、コンパイラーはこのプロモーションを自由に最適化できます。これにより、乗算して完全な64ビット結果を取得する前に32ビット整数を64ビットにキャストするなどのイディオムが発生します。プロモーションは少し混乱し、符号付きと符号なしの値が混在していると予期しない結果になる可能性があります。非公式に説明するのは難しいので、知りたい場合は調べてみてください。

于 2010-07-13T05:55:18.407 に答える
2

心配な場合は、16ビットの符号なし整数<stdint.h>など、定義された長さの型を含めて使用できます。uint16_t

于 2010-07-13T05:46:04.323 に答える
2

あなたのコードは完全に有効です(他の人がすでに言っているように)。ほとんどの場合、移植可能な方法でプログラムしたい場合は、裸のCタイプintを使用するべきではありませんが、それを使って何をしようとしているのかを少しよく伝えるタイプを使用する必要がありますlongunsigned int

たとえば、配列のインデックスの場合は常にを使用しますsize_t。32ビットまたは64ビットシステムを使用しているかどうかに関係なく、これは適切なタイプになります。または、プラットフォームで最大幅の整数を取得したい場合は、たまたま使用時に着陸しintmax_tますuintmax_t

于 2010-07-13T06:08:11.893 に答える
1

http://gcc.gnu.org/ml/gcc-help/2003-06/msg00086.htmlを参照してください-コードは完全に有効なC/C++です。

このタイプの切り捨てを確認するには、静的分析ツール(sparse、llvmなど)を確認することをお勧めします。

于 2010-07-13T05:54:30.983 に答える