2017-01-31 5 views
0

だから私は次のようなコードがある場合: Cでtypedefされた共用体の構造体を初期化するにはどうしたらいいですか?

typedef union { 
    long integer; 
    float decimal; 
    long *integerPtr; 
    float *decimalPtr; 
} Number; 

typedef struct Point { 
    Number x; 
    Number y; 
} Point; 

がどのように私はこれを初期化しますか?それは次のように簡単ですか?私もconstでこれを行うことはできますか?

Point p = { 100, 100 }; 
const Point p2 = { 640, 200 }; 

int someNum, someOtherNum; 

Point p3 = { &someNum, &someOtherNum }; 

FYI:具体的には、C99のCコードより前のものです。

+0

は、C君のバージョンのタグを追加します。しかしとして厳格なエイリアシング規則を使用すると、float型のサイズと同じである長いの大きさを提供し、タイプpunningを使用しようとすることができます適用されません。ターゲット。一般的に、古代のCコードは書いてはいけませんが、C99で始まった現代のCを使ってください。これは指定された初期化子をサポートしており、最初のメンバだけでなく '共用体 'も初期化できます。 Re。あなたの質問: 'union'をどのように初期化したいのかははっきりしません。そして、「constでこれをやってもいいですか?」とどういう意味ですか?あなたのコードはどのような組合員が現在アクティブであるかを知ることになっていますか? – Olaf

+1

'ポイントp = {{100}、{100}};で十分ですか? 'integer'フィールドを初期化します。 – chux

答えて

1

コンパイラを対象にしている場合は、ユニオンの最初の要素のみを初期化することができます。いい部分は、厳密なエイリアシング規則で悩まされないことです。長い話を短く、ここでは何が起こるかです:

  • は整数値で初期化:すべての罰金ですlitteralまたは変数はlongに変換されますので、これは正常に動作します:

    Point p = { 100, 100 }; 
    const Point p2 = { 640, 200 }; 
    
  • ポインタで初期化する:longフィールドはlongに変換されたポインタの値を受け取ります。実際に何が起きるかは不明ですが、リトルエンディアンの共通アーキテクチャーでは、ポインタが長いほど、またはポインターと同じサイズを持ち、ポインターの表現が整数アドレスの場合は、すべてが問題ありません。実際にはlong値を初期化しますが、longと同じ表現であるポインタ表現として期待される結果が得られます。 (共通のアーキテクチャ上で)予想通りだからここに再び、これは動作します:

    int someNum, someOtherNum; 
    Point p3 = { &someNum, &someOtherNum }; 
    
  • 山車で初期化:longにfloat型の変換のために直接的な方法は、限りない同じ表現を持っていません。

    float f=12.5, g=1.; 
    Point p4 = { *((long *) &f), *((long *) &g) }; 
    
+0

ありがとう!ニース簡潔な答え。 – nyteshade

関連する問題