Gör så här: Ändra uttrycksträd (Visual Basic)
Det här avsnittet visar hur du ändrar ett uttrycksträd. Uttrycksträd är oföränderliga, vilket innebär att de inte kan ändras direkt. Om du vill ändra ett uttrycksträd måste du skapa en kopia av ett befintligt uttrycksträd och göra de nödvändiga ändringarna när du skapar kopian. Du kan använda ExpressionVisitor klassen för att korsa ett befintligt uttrycksträd och kopiera varje nod som den besöker.
Ändra ett uttrycksträd
Skapa ett nytt konsolprogramprojekt .
Lägg till en
Imports
-instruktion i filen förSystem.Linq.Expressions
namnområdet.Lägg till klassen i
AndAlsoModifier
projektet.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
Den här klassen ärver ExpressionVisitor klassen och är specialiserad på att ändra uttryck som representerar villkorsstyrda
AND
åtgärder. De här åtgärderna ändras från en villkorligAND
till en villkorsstyrdOR
. För att göra detta åsidosätter VisitBinary klassen metoden för bastypen, eftersom villkorsuttryckAND
representeras som binära uttryck.VisitBinary
Om uttrycket som skickas till metoden i metoden representerar en villkorsstyrdAND
åtgärd konstruerar koden ett nytt uttryck som innehåller villkorsoperatornOR
i stället för den villkorsstyrdaAND
operatorn. Om uttrycket som skickas tillVisitBinary
inte representerar en villkorsstyrdAND
åtgärd defersar metoden till basklassimplementeringen. Basklassmetoderna konstruerar noder som liknar de uttrycksträd som skickas in, men noderna får sina underträd ersatta med de uttrycksträd som genereras rekursivt av besökaren.Lägg till en
Imports
-instruktion i filen förSystem.Linq.Expressions
namnområdet.Lägg till
Main
kod i metoden i filen Module1.vb för att skapa ett uttrycksträd och skicka den till den metod som ska ändra den.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"))
Koden skapar ett uttryck som innehåller en villkorsstyrd
AND
åtgärd. Sedan skapas en instans avAndAlsoModifier
klassen och uttrycket skickas till metoden för denModify
här klassen. Både det ursprungliga och det ändrade uttryckets träd matas ut för att visa ändringen.Kompilera och kör programmet.