私はこのようないくつかのCコードを見た:Cの構造体に1つの基本フィールドのみをカプセル化する利点は何ですか?
// A:
typedef uint32_t in_addr_t;
struct in_addr { in_addr_t s_addr; };
を私は常にこのよう好む:
// B:
typedef uint32_t in_addr;
だから私の質問は:BからAにそれをやっての違い/利点は何ですか?
私はこのようないくつかのCコードを見た:Cの構造体に1つの基本フィールドのみをカプセル化する利点は何ですか?
// A:
typedef uint32_t in_addr_t;
struct in_addr { in_addr_t s_addr; };
を私は常にこのよう好む:
// B:
typedef uint32_t in_addr;
だから私の質問は:BからAにそれをやっての違い/利点は何ですか?
タイプセーフティを導入するためのレイヤーで、将来の拡張に役立ちます。
前者の1つの問題は、typedefed組み込み関数によって表される型の値を、他のいくつかの型またはtypedefed組み込み関数のいずれかに '変換'することが容易であることです。
を考える:
対:
// field notation could vary greatly here:
struct t_millisecond { int ms; };
struct t_second { int s; };
struct t_degrees { int f; };
いくつかのケースでは、それは少し明確に表記を使用することができ、およびコンパイラは、誤った変換を禁止します。検討:
int a = millsecond * second - degree;
これは疑わしいプログラムです。 typedefed intを使用して、それは有効なプログラムです。構造体を使用すると、不正な形式になります。コンパイラエラーはあなたの修正を必要とし、意図を明確にすることができます。
typedefを使用すると、任意の算術演算と変換が適用され、警告なしで互いに割り当てられている可能性があります。
も考えてみましょう:
t_second s = millisecond;
も致命的な変換されること。
これはツールボックス内の別のツールです。あなたの裁量で使用します。
ジャスティンの答えは本質的に正しいですが、私はいくつかの拡張が必要だと思っています。
編集:ジャスティンは、これをいくらか冗長にする彼の答えを大幅に拡大しました。
型の安全性 - データを操作するAPI関数をユーザーに提供したいだけで、整数として扱うことはできません。フィールドを構造体に隠すと、間違った方法で使用することが難しくなり、ユーザーを適切なAPIに近づけることができます。
今後の拡張のために、将来の実装では物事を変更したいと思うかもしれません。おそらく、フィールドを追加するか、既存のフィールドを4文字に分割します。構造体では、これはAPIを変更することなく行うことができます。
とは何ですか?実装が変更された場合、コードが破損しないこと。
+1あなたの説明も良いです – justin
ありがとうございました。 –
安全のために、誤った型キャスティングを避けるためのものですか?拡張のために、私は単純なtypedefを構造体に変更することをお勧めします。 –
+1しかし、私は彼が例なしで理解するだろうか分からない! :) –
@paladin_t:浮動小数点値を 'uint32_t'に代入すると、いくつかの警告が出ますので、代入を行います。しかし、これは構造体では不可能です。 – dirkgently