初めて C# を学んだとき、C/C++ にあるのと同じ機能のマクロがサポートされていないことに驚きました。C# にも #define キーワードがあることはわかっていますが、C/C++ で気に入っていた機能と比べると、大幅に欠けています。なぜかご存じの方はいらっしゃいますか。本物C# にマクロがありませんか?
この質問がすでに何らかの形で尋ねられている場合はお詫び申し上げます。投稿する前に、重複した質問を探すのに 5 分も費やしたとお約束します。
ベストアンサー1
C# の FAQ より。
http://blogs.msdn.com/CSharpFAQ/archive/2004/03/09/86979.aspx
C# はなぜ #define マクロをサポートしないのでしょうか? C++ では、次のようなマクロを定義できます。
#define PRODUCT(x, y, z) x * y * z
そしてそれをコードで使用します:
int a = PRODUCT(3, 2, 1);
C# ではこれができません。なぜでしょうか?
理由はいくつかあります。まずは読みやすさです。
C# の主な設計目標の 1 つは、コードを非常に読みやすくすることです。マクロを記述できるということは、プログラマーが独自の言語を作成できることを意味します。その言語は、必ずしも下にあるコードと関係があるわけではありません。コードの動作を理解するには、ユーザーは言語の動作を理解するだけでなく、その時点で有効な #define マクロをすべて理解する必要があります。そのため、コードが読みにくくなります。
C# では、マクロの代わりにメソッドを使用できます。ほとんどの場合、JIT によってメソッドがインライン化されるため、同じパフォーマンス面が得られます。
もう少し微妙な問題もあります。マクロはテキストで実行されるため、次のように記述すると、
int y = PRODUCT (1 + 2, 3 + 4, 5 + 6)
となるものを期待します
3 * 7 *11 = 231
が、実際には、私が定義した展開により次のようになります。
int y = 1 + 2 * 3 + 4 * 5 + 6;
結果は 33 になります。括弧をうまく使えばこの問題は回避できますが、状況によっては機能し、他の状況では機能しないマクロを記述するのは非常に簡単です。
C# には厳密に言えばプリプロセッサはありませんが、コンパイルに影響を与えるために使用できる条件付きコンパイル シンボルがあります。これらはコード内またはコンパイラへのパラメータで定義できます。C# の「プリプロセス」ディレクティブ (個別のプリプロセス手順がないにもかかわらず、C/C++ との一貫性を保つためにのみ命名されています) は次のとおりです (テキストは ECMA 仕様から引用)。
#define and #undef
条件付きコンパイルシンボルの定義と定義解除に使用されます
#if, #elif, #else and #endif
ソースコードのセクションを条件付きでスキップするために使用される
#line
エラーや警告に対して発行される行番号を制御するために使用されます。
#error and #warning
エラーや警告を発行するために使用されます。
#region and #endregion
ソースコードのセクションを明示的にマークするために使用されます。
上記の詳細については、ECMA 仕様のセクション 9.5 を参照してください。条件付きコンパイルは、メソッドの Conditional 属性を使用して実現することもできます。これにより、適切なシンボルが定義されている場合にのみ、メソッドの呼び出しがコンパイルされます。詳細については、ECMA 仕様のセクション 24.4.2 を参照してください。
著者: エリック・ガンナーソン