.NET ランタイムによる式ツリーのサポート
.NET ランタイムには、式ツリーを使用するクラスが多くあります。 クラスの全リストは System.Linq.Expressions で確認できます。 ここでは、そのすべてを列挙するのではなく、ランタイム クラスがどのように設計されているのかを説明します。
言語設計の観点から言えば、式は、評価して値を返すコードの本体です。 式は単純な場合があります。定数式 1
は定数値 1 を返します。 式が複雑になる場合もあります。式 (-B + Math.Sqrt(B*B - 4 * A * C)) / (2 * A)
は二次方程式の 1 つの解を返します (式に解がある場合)。
System.Linq.Expression と派生型
式ツリーの使用が複雑になる理由の 1 つは、プログラムの多くの場所でさまざまな種類の式が有効になることです。 代入式を考えてみます。 代入式の右側には、定数値、変数、メソッドの呼び出し式、その他を含めることができます。 言語に柔軟性があるため、式ツリーをたどっていくと、ツリーのノードのあらゆる場所でさまざまな式の型が使用されていることに気づくはずです。 そのため、基本の式の型を使用できるときは、それが最も簡単な操作方法です。 しかし、場合によっては、それ以上の知識が必要です。 このために、基本の式クラスに NodeType
プロパティが含まれています。 それによって返される ExpressionType
は、可能な式の型の列挙型です。 ノードの型がわかったら、その型にキャストし、式ノードの型を識別する特定のアクションを実行します。 特定の型のノードを検索し、その種類の式が持つ特定のプロパティを使用できます。
たとえば、次のコードでは変数アクセス式の変数名を出力します。 次のコードでは、ノードの型を調べてから、変数アクセス式にキャストした後、特定の式の型のプロパティを調べる手順を示します。
Expression<Func<int, int>> addFive = (num) => num + 5;
if (addFive is LambdaExpression lambdaExp)
{
var parameter = lambdaExp.Parameters[0]; -- first
Console.WriteLine(parameter.Name);
Console.WriteLine(parameter.Type);
}
式ツリーを作成する
System.Linq.Expression
クラスには、式を作成する静的メソッドも数多く含まれています。 これらのメソッドは、その子に指定された引数を使用して式ノードを作成します。 このようにして、リーフ ノードから式を作成します。 たとえば、次のコードは Add 式を作成します。
// Addition is an add expression for "1 + 2"
var one = Expression.Constant(1, typeof(int));
var two = Expression.Constant(2, typeof(int));
var addition = Expression.Add(one, two);
この簡単な例からわかるように、さまざまな型が式ツリーの作成と操作に関わっています。 C# 言語が備える豊富な語彙が提供する機能を発揮するには、こうした複雑さが必要になります。
API を探す
ほぼすべての C# 言語の構文要素に対してマップされる式ノード型がそれぞれ存在します。 各型には、その型の言語要素に特有のメソッドがあります。 一度に覚えておくべきことがたくさんあります。 式ツリーを操作するときは、すべてを憶えておくのではなく、次に示す手法を使います。
ExpressionType
列挙型のメンバーを調べて、検証するノードを特定します。 このリストは、式ツリーを走査して理解するときに役立ちます。Expression
クラスの静的メンバーを調べて、式を作成します。 これらのメソッドでは、その子ノードから任意の式の型を作成できます。ExpressionVisitor
クラスを調べて、変更された式ツリーを作成します。
それら 3 つの部分を調べれば、さらに多くのことがわかります。 それら 3 つのステップのいずれかから始めると、必要なことが必ず見つかります。
.NET
フィードバック
https://aka.ms/ContentUserFeedback」を参照してください。
以下は間もなく提供いたします。2024 年を通じて、コンテンツのフィードバック メカニズムとして GitHub の issue を段階的に廃止し、新しいフィードバック システムに置き換えます。 詳細については、「フィードバックの送信と表示