さらにコードを書き続けると、コードを整理するのが難しくなることがあります。
これがあなたの問題です。組織を正しくし、スタイルをより簡単に流すべきです。
しないでください待って、あなたのコードを整理するために:あなたが行くように整理してコードを保持します。言語はあなたのためにそれをしませんが、コードは依然として低結合と高凝集度を持つモジュールに編成されるべきです。
これらのモジュールは、当然名前空間を提供します。モジュール名を短縮し(長い場合)、衝突を避けるために、モジュールに関数名のプレフィックスを付けます。
個々の識別子のレベルでは、これらはおおむね主観の昇順です。
- コンベンションを選んで、それに固執する
- 例えば、
function_like_this(struct TypeLikeThis variable)
一般的です
ハンガリー語の表記は絶対に避けてください(JNLに申し訳ありません)
純粋に不透明なCookieタイプでない限り、ポインターのtypedefは避けてください-物事を混乱させるだけです
struct Type *ok;
typedef struct Type *TypePtr;
TypePtr yuck;
不透明なCookieタイプとはどういう意味ですか?つまり、モジュール(またはライブラリなど)内で使用され、クライアントコードに渡される必要があるものを意味しますが、そのクライアントコードは直接使用できません。それをライブラリに渡すだけです。
たとえば、データベースライブラリは次のようなインターフェイスを公開します。
/* Lots of buffering, IPC and metadata magic held in here.
No, you don't get to look inside. */
struct DBContextT;
/* In fact, you only ever get a pointer, so let's give it a nice name */
typedef struct DBContexT *DBContext;
DBContext db_allocate_context(/*maybe some optional flags?*/);
void db_release_context(DBContext);
int db_connect(DBContext, const char *connect);
int db_disconnect(DBContext);
int db_execute(DBContext, const char *sql);
これで、内部を見ることができないため、コンテキストはクライアントコードに対して不透明になります。それをライブラリに渡すだけです。そのようなFILE
ものも不透明であり、整数ファイル記述子もCookieですが、不透明ではありません。
設計上の注意
私は説明なしで低結合と高凝集度というフレーズを使用しましたが、それについて少し気分が悪いです。あなたはそれを検索し、おそらくいくつかの良い結果を見つけることができますが、私は簡単にそれに対処しようとします(もう一度、エッセイを書くことができますが、しようとしません)。
上にスケッチしたDBライブラリは、小さなインターフェースを外部に公開するため、結合が低いことを示しています。実装の詳細を(部分的に不透明なCookieトリックを使用して)隠すことにより、クライアントコードがそれらの詳細に依存するのを防ぎます。
不透明なCookieの代わりに、そのコンテンツが見えるようにコンテキスト構造体を宣言し、データベースへのTCP接続用のソケットファイル記述子が含まれていると想像してください。DBが同じマシンで実行されているときに共有メモリセグメントの使用をサポートするように実装を後で変更する場合、クライアントは単に再リンクするのではなく、再コンパイルする必要があります。さらに悪いことに、クライアントはファイル記述子の使用を開始することもできました。たとえばsetsockopt
、デフォルトのバッファサイズを変更するために呼び出した場合、コードの変更も必要になります。これらの詳細はすべて、実用的な場合はモジュール内に隠し、モジュール間の結合を低くする必要があります。
この例では、モジュール内のすべてのメソッドが同じタスク(DBアクセス)に関係しているという点で、高い凝集度も示しています。これは、実装の詳細(つまり、Cookieの内容)について知る必要があるコードのみが実際にアクセスできることを意味し、デバッグを簡素化します。
また、単一の懸念事項があることで、これらの機能をグループ化するプレフィックスを簡単に選択できることもわかります。
さて、この例が良いと言うのは簡単です(特に完全ではないので)が、すぐには助けにはなりません。トリックは、コードを記述して拡張する際に、同様のことを行う関数や同じタイプで動作する関数(独自のモジュールの候補になる可能性がある)、および多くの別個のことを行う関数を監視することです。本当に関連しており、分割の候補になるかもしれません。