0

私は int を void* にキャストすることを比較しようとしましたが、それらの間の比較さえも

int i=1,j=2;
float a=1.1;

if((void *)i > (void *)j )
cout<<"i>j"<<endl;
else
cout<<"i<j"<<endl;

出力は

i<j

でもこれは

if((void *)a > (void *)i )
cout<<"a>i"<<endl;
else
cout<<"a<i"<<endl;

エラーを与える

 error: invalid cast from type ‘float’ to type ‘void*’

何でもキャストして void ポインターにできると思っていたのですが、そうではないでしょうか?

4

4 に答える 4

5

void ポインタの比較、それは定義されているか、コンパイラに依存していますか?

これは明確に定義されていますが、C++11 5.9/3 で説明されているように、結果は通常指定されていません。または >= であり、それ以外の場合は false。それ以外の場合、結果は指定されていません。」

std::lessビルトイン演算子が定義していない場合でも、ポインタの全体的な順序を定義するためにフレンドが必要であることに注意してください。

ただし、任意の整数値から変換したポインターを使用して何かを行うと、未定義の動作が発生します。

何でもキャストして void ポインターにできると思っていたのですが、そうではないでしょうか?

いいえreinterpret_cast(または同等の C スタイルのキャスト) は、ポインター型と整数型の間で変換できます。浮動小数点値をポインターに変換しても意味がありません。

于 2013-09-03T16:51:02.617 に答える
3

何でもキャストして void ポインターにできると思っていたのですが、そうではないでしょうか?

Aは、任意の型ではなく、任意のオブジェクト ポインター型void*との間でキャストできるようにすることを目的としています。

これは、次のことができることを意味します。

if((void *)&a > (void *)&i )

ただし、このようなポインター値のチェックと比較が役立つことはほとんどありません。

于 2013-09-03T16:46:53.717 に答える
1

「何でも」(関数ではない、または「アドレス」がメンバーへのポインターによって指定される) のアドレスを にキャストできますvoid *。さらに、一部の整数型はポインターにキャストできます。あなたがやりたかったのはこれだと思います

if((void *)&i > (void *)&j )
    cout<<"i>j"<<endl;
else
    cout<<"i<j"<<endl;

そしてそれ

if((void *)&a > (void *)&i )
    cout<<"a>i"<<endl;
else
    cout<<"a<i"<<endl;

ただし、このようなポインター比較の結果は、C++11 5.9/3 では規定されていないことに注意してください ( Mike Seymour投稿.

同じ型のポインターを比較する最良の方法は、テンプレートgreaterlessgreater_equalおよびless_equal20.8.5/8 が言うため、を使用することです。

テンプレートgreaterlessgreater_equal、およびの場合、任意のポインター型の特殊化により、組み込み演算子、、がそうでないless_equal場合でも、全体の順序が得られます。<><=>=

したがって、使用する必要があります

if (std::greater<void*>()((void *) &i, (void *) &j))
    cout<<"i>j"<<endl;
else
    cout<<"i<j"<<endl;
于 2013-09-03T16:48:43.577 に答える
1

オブジェクト ポインター型は、どの型にもキャストできvoid*ません。

したがって、次の方法で問題を解決できます。

if((void *)&a > (void *)&i )
//         ^            ^

しかし、2 つの変数のアドレスを比較することは、値を比較することと同じではありません。あなたが望む結果が得られるとは思いません...ここで未定義の動作が発生します。

于 2013-09-03T16:51:07.127 に答える