2010-07-05 14 views
6

Bevor jemand die Antwort schreit, lesen Sie bitte die Frage durch.Was bedeutet ExpressionVisitor.Visit <T>?

Was ist der Zweck des Verfahrens in Expression .NET 4.0 ist:

public static ReadOnlyCollection<T> Visit<T>(ReadOnlyCollection<T> nodes, Func<T, T> elementVisitor) 

Meine erste Vermutung über den Zweck dieses Verfahrens war, dass es jeden Knoten in jedem Baum durch die nodes angegeben besuchen würde Parameter und schreiben Sie den Baum mit dem Ergebnis der elementVisitor Funktion neu.

Dies scheint nicht der Fall zu sein. Eigentlich scheint diese Methode ein wenig mehr als nichts zu tun, es sei denn, ich vermisse hier etwas, was ich stark vermute ...

Ich habe versucht, diese Methode in meinem Code zu verwenden und wenn die Dinge nicht geklappt haben Wie erwartet, übertrug ich die Methode und fand:

public static ReadOnlyCollection<T> Visit<T>(ReadOnlyCollection<T> nodes, Func<T, T> elementVisitor) 
{ 
    T[] list = null; 
    int index = 0; 
    int count = nodes.Count; 
    while (index < count) 
    { 
     T objA = elementVisitor(nodes[index]); 
     if (list != null) 
     { 
      list[index] = objA; 
     } 
     else if (!object.ReferenceEquals(objA, nodes[index])) 
     { 
      list = new T[count]; 
      for (int i = 0; i < index; i++) 
      { 
       list[i] = nodes[i]; 
      } 
      list[index] = objA; 
     } 
     index++; 
    } 
    if (list == null) 
    { 
     return nodes; 
    } 
    return new TrueReadOnlyCollection<T>(list); 
} 

Also wo würde jemand tatsächlich mit dieser Methode gehen? Was fehlt mir hier?

Danke.

Antwort

3

Es sieht für mich wie eine bequeme Methode aus, um eine Arbitrary-Transformationsfunktion auf einen Ausdrucksbaum anzuwenden und den resultierenden transformierten Baum oder den ursprünglichen Baum zurückzugeben, wenn es keine Änderung gibt.

Ich kann nicht sehen, wie dies ein Muster anders als ein Standard-Ausdruck Besucher ist, außer außer mit einem Besuchertyp verwendet es eine Funktion.

Was Nutzung:

Expression<Func<int, int, int>> addLambdaExpression= (a, b) => a + b; 

// Change add to subtract 
Func<Expression, Expression> changeToSubtract = e => 
{ 
    if (e is BinaryExpression) 
    { 
     return Expression.Subtract((e as BinaryExpression).Left, 
            (e as BinaryExpression).Right); 
    } 
    else 
    { 
     return e; 
    } 
}; 

var nodes = new Expression[] { addLambdaExpression.Body }.ToList().AsReadOnly(); 
var subtractExpression = ExpressionVisitor.Visit(nodes, changeToSubtract); 

Sie erklären nicht, wie Sie es erwartet verhalten und warum deshalb denken Sie, es tut wenig mehr als nichts.

+1

Ich hätte erwartet, dass es den gesamten Baum in addLambdaExpression besucht, nicht nur LambdaExpression selbst hinzufügen. – Jeff

+0

In diesem Fall sollten Sie einen benutzerdefinierten Typ von ExpressionVisitor erben und die NodeType.Lambda in der Visit() -Methode behandeln. – codekaizen