Como modificar árvores de expressão (C# e Visual Basic)
Este tópico mostra como modificar uma árvore de expressão. Árvores de expressão são imutáveis, o que significa que eles não podem ser modificados diretamente. Para alterar uma árvore de expressão, você deve criar uma cópia de uma árvore de expressão existente e quando você cria a cópia, faça as alterações necessárias. Você pode usar o ExpressionVisitor classe para percorrer uma árvore de expressão existente e copiar a cada nó em que ele visita.
Dica
Você pode encontrar o código-fonte para o ExpressionVisitor de classe na CodePlex site da Web.
Para modificar uma árvore de expressão
Na Visual Studio, crie um novo Aplicativo de Console project.
Adicionar o AndAlsoModifier classe ao seu projeto.
Esta classe herda de ExpressionVisitor de classe e é especializado para modificar as expressões que representam condicional AND as operações. Ele altera essas operações de uma condicional AND para uma condicional OR. Para fazer isso, as substituições de classe a VisitBinary o método do tipo base, porque condicional AND expressões são representadas como expressões binárias. No VisitBinary método, se a expressão que é passada para ele representa uma condicional AND operação, o código cria uma nova expressão que contém o condicional OR o operador em vez da condicional AND operador. Se a expressão que é passada para VisitBinary não representa uma condicional AND operação, o método adia a implementação de classe base. Os métodos de classe base, nós de construção que são como as árvores de expressão que são passadas em, mas os nós têm suas árvores de sub substituídos com as árvores de expressão são produzidos recursivamente pelo visitante.
Adicionar um using diretiva (ou Imports instrução em Visual Basic) o arquivo para o System.Linq.Expressions espaço para nome.
Public Class AndAlsoModifier Inherits ExpressionVisitor Public Function Modify(ByVal expr As Expression) As Expression Return Visit(expr) End Function Protected Overrides Function VisitBinary(ByVal b As BinaryExpression) As Expression If b.NodeType = ExpressionType.AndAlso Then Dim left = Me.Visit(b.Left) Dim right = Me.Visit(b.Right) ' Make this binary expression an OrElse operation instead ' of an AndAlso operation. Return Expression.MakeBinary(ExpressionType.OrElse, left, right, _ b.IsLiftedToNull, b.Method) End If Return MyBase.VisitBinary(b) End Function End Class
public class AndAlsoModifier : ExpressionVisitor { public Expression Modify(Expression expression) { return Visit(expression); } protected override Expression VisitBinary(BinaryExpression b) { if (b.NodeType == ExpressionType.AndAlso) { Expression left = this.Visit(b.Left); Expression right = this.Visit(b.Right); // Make this binary expression an OrElse operation instead of an AndAlso operation. return Expression.MakeBinary(ExpressionType.OrElse, left, right, b.IsLiftedToNull, b.Method); } return base.VisitBinary(b); } }
Adicione código para o Main método no arquivo Program. cs (Module1. vb no Visual Basic) para criar uma árvore de expressão e passá-lo para o método que irá modificá-lo.
O código a seguir cria uma expressão que contenha uma condicional AND operação. Em seguida, ele cria uma instância da AndAlsoModifier de classe e passa a expressão para o Modify método dessa classe. As árvores de expressão modificado e originais são saídas para mostrar a alteração.
Adicionar um using diretiva (ou Imports instrução em Visual Basic) o arquivo para o System.Linq.Expressions espaço para nome.
Dim expr As Expression(Of Func(Of String, Boolean)) = _ Function(name) name.Length > 10 AndAlso name.StartsWith("G") Console.WriteLine(expr) Dim modifier As New AndAlsoModifier() Dim modifiedExpr = modifier.Modify(CType(expr, Expression)) Console.WriteLine(modifiedExpr) ' This code produces the following output: ' name => ((name.Length > 10) && name.StartsWith("G")) ' name => ((name.Length > 10) || name.StartsWith("G"))
Expression<Func<string, bool>> expr = name => name.Length > 10 && name.StartsWith("G"); Console.WriteLine(expr); AndAlsoModifier treeModifier = new AndAlsoModifier(); Expression modifiedExpr = treeModifier.Modify((Expression) expr); Console.WriteLine(modifiedExpr); /* This code produces the following output: name => ((name.Length > 10) && name.StartsWith("G")) name => ((name.Length > 10) || name.StartsWith("G")) */
Compile e execute o aplicativo.
Consulte também
Tarefas
Como executar árvores de expressão (C# e Visual Basic)