0

私はbox2dの初心者で、b2bodyオブジェクトのuserdata(void *型)フィールドを使用してint値(enum値なので、オブジェクトの型がわかります)を格納しようとしています。

今、私はこれをやっています:

int number = 1023;

void* data = (void*)(&number);

int rNumber = *(int*)data;

そして、私は値を正しく取得しますが、void * へのキャストについて読んでいるので、移植可能でも推奨可能でもありません...私のコードはクロスプラットフォームですか? それは動作が定義されているか、実装に依存していますか?

ありがとう!

4

5 に答える 5

4

へのキャストvoid *は移植可能です。型の安全性が失われるため、お勧めしません。には何でも入れることがvoid *でき、何でも取り出すことができます。自分の足を撃ちやすくなります。それ以外の場合void *は、慎重で特別な注意を払っている限り問題ありません。

于 2012-07-25T07:45:27.577 に答える
2

あなたは実際には にキャストしているのではなく、 にキャストintしていますが、これはまったく異なります。void*int*void*

任意の型へのポインターを に格納し、同じvoid*に再度キャストすることができます。それは動作することが保証されています。

言語標準では、異なるポインターが同じサイズでなければならない、または同じように機能する必要があるとは言われていないため、他の型へのキャストは移植性がありません。それらvoid*を収容するのに十分な幅が必要です。

于 2012-07-25T08:04:51.193 に答える
1

void *はどういうわけか過去の遺物(ISO C)ですが、非常に便利です。必要なタイプを慎重に前後にキャストする限り、安全に使用できます。C++クラスシステムや関数のオーバーロードなどの他の代替案を検討してください

とにかく、より良いキャスト演算子があります。他の方法がない場合(void *)もあれば、便利すぎる場合もあります。

それは、キャスティングシステムのためではなく、一部の人々がそれらを使って移植性のない操作をしたいという誘惑のために、移植性のないコードにつながる可能性があります。最大の問題は、(void *)がメモリアドレスと同じくらい大きいという事実にあります。これは、多くのプラットフォームでは、プラットフォームの整数の長さでもあります。

ただし、いくつかのまれな例外では、size(void *)!= size(int)

必要なタイプにキャストバックせずに、あるタイプの操作/マジックを実行しようとすると、問題が発生する可能性があります。整数をvoid*ポインタに格納したいと思っている人を何度も見たことがあることに驚かれるかもしれません。

于 2012-07-25T07:57:47.630 に答える
1

問題の 1 つは、void*適切にキャストするために、元の型を知る (追跡する) 必要があることです。元々が でfloatあり、それを にケース化した場合int、コンパイラはあなたの言葉を受け入れるだけです。

これを回避するには、型を含むデータのラッパーを作成することができます。そうすれば、常に正しい型にキャストできます。

編集: C ie の代わりに C++ のキャスト スタイルを使用する習慣も身に付ける必要があります。reinterpret_cast

于 2012-07-25T07:47:49.350 に答える