2012-05-03 17 views
2

私はかなり理解していないCコードを見つけました。以下はコンパイルして動作します。 1)なぜstruct *にchar *をキャストできますか?2)void *の代わりにこのイディオムを使用する利点はありますか?char * ptr to struct

struct foo 
{ 
    int a; 
    int b; 
    char *nextPtr; 
}; 

. . . 

// This seems wrong 
char *charPtr = NULL; 

// Why not 
//void *structPtr = NULL; 

struct foo *fooPtr; 
fooPtr = (struct foo*)charPtr; 

//実際に問題のポイントではないので、文字列部分を削除して編集します。

+0

「文字列」とは何ですか?これはCかC++ですか? – dirkgently

+2

Cスタイルのキャスト構文を使って何かにキャストすることができます。コンパイラはあなたを信頼します。代わりに 'char *'が使われた 'void *'が発明されるまでに時間がありましたが、その時はすでに経過しています。 – Flexo

+1

申し訳ありませんが、もしそれが適切です。 – LeviX

答えて

1
  1. ポインタタイプ間で変換することができます。これは、これが言語の柔軟性を提供するためです。しかし、あなたは慎重で、あなたがやっていることや問題がある可能性があることを知るべきです。

  2. いいえ変換が必要ないようにプロパティポインタ型を使用する利点があります。それが不可能な場合は、void *を使用するかどうかは関係ありませんが、コードを読んでいる開発者にとっては少しはっきりしているかもしれません。アドレスを保持しているだけで、変数 -

+1

char *を使用すると、構造体の要素を 'printf(" * fooPtr contains%s \ n "、charPtr)のように1つの文で出力するためのデバッグを目的としています。 –

+1

@AhmedJolani:恐ろしいデザインのようです。構造体には、印刷できない文字に変換するデータが含まれている可能性があります。 –

+0

によると、2つの整数はNULL値\ x00を持つことはありません。* nextPtrがNULLの場合、printfは値を完全に記述し、整数は常に印字可能な文字(数字)を持ちます。 –

0

私はあなただけで実際にはC.

のそれらの古典的な「両刃の剣」の1渡って来ている、ポインタはポインタだと思います。あなたは、理論的には、そのポインタが何かを指すように強制することができます。構造体、int、a(空白を埋める)。あるものへのポインタを別のものへのポインタにキャストしようとすると、Cは文句を言うことはありません。それはあなたが何をやっているのかを理解しています。天国は助けてくれないでしょう:)

実際、何かの隣を指すポインターを宣言するのは恐らく空き*でしょうが、それは大きな違いがあるかどうかはわかりません操作中です。コンパイラの最適化があり、ポインタが強く型付けされている場合に起こる可能性があるため、その点までは誓いません...

1

1)前述のように、Cの任意のポインタ型にキャストすることができます。より複雑なルールを有していてもよく、私は認識していないよその詳細)...

2)char*void*対の利点は、あなたがchar*ではなくvoid*を上ポインタ演算を行うことができるということです。

ポインタ演算を行う上での知恵は、あなたが投稿したコードに基づいて疑わしいかもしれませんが、可変長の 'データ'を持つ構造体ではしばしば便利です。