2009-08-14 5 views
5

Je souhaite utiliser l'expression Linq pour certaines fonctions dynamiques. J'ai besoin d'expressions And, Or et Not .. Je ne pouvais pas obtenir beaucoup ..C# Expression utilisant l'expression Et Ou et Non ensemble basée sur AST

Nous voulons vérifier si certaines fonctionnalités ont été activées ou non dans notre système et sur la base de cela, nous déciderons de montrer ou non l'élément de menu ou pas. Nous avons formé des règles au format XML, je sais convertir la règle en AST mais je ne sais pas comment mapper l'expression Linq.

Les règles sont comme: Feature1Enabled Et Feature2Eenabled ou (Feature3Disabled et non Feature5Enabled)

ici "Feature1Enabled", "Feature2Eenabled" etc sont le nom de la fonction. Nous allons passer cette chaîne à la fonction IsFeatureEnabled pour vérifier si une fonctionnalité a été activée ou non.

public delegate bool IsEnabledDelegate(string name, string value); 

    public static bool IsFeatureEnabled(string name, string value) 
    { 
     if (name == "MV") 
      return true; 

     if (name == "GAS" && value == "G") 
      return true; 
     //More conditions goes here 
     return false; 
    } 

    static void Main(string[] args) 
    { 
     Expression<Func<string, string, bool>> featureEnabledExpTree = 
         (name, value) => IsFeatureEnabled(name, value); 

     //I want the equal of the following statement in C# Linq Expression 

     bool result = IsFeatureEnabled("MV", "") && IsFeatureEnabled("GAS", "G") || !IsFEatureEnabled("GAS", "F") 

    } 

Je veux l'équivalent au résultat bool = IsFeatureEnabled ("MV", "") & & IsFeatureEnabled ("GAZ", "G") || ! IsFEatureEnabled ("GAZ", "F")

dans l'expression Linq Format .. Cependant, je peux les convertir en dynamique en fonction de mes notations AST ..

Merci beaucoup .. Si vous avez besoin de plus d'informations , dites-moi dans les commentaires ..

+0

(exemple révisé pour montrer featureEnabledExpTree de construction lors de l'exécution à partir des données) –

Répondre

4
ParameterExpression name = Expression.Parameter(typeof(string), "name"), 
     value = Expression.Parameter(typeof(string), "value"); 

    // build in reverse 
    Expression body = Expression.Constant(false); 
    body = Expression.Condition(
     Expression.AndAlso(
      Expression.Equal(name, Expression.Constant("GAS")), 
      Expression.Equal(value, Expression.Constant("G")) 
     ), Expression.Constant(true), body); 
    body = Expression.Condition(
     Expression.Equal(name, Expression.Constant("MV")), 
     Expression.Constant(true), body); 

    Expression<Func<string, string, bool>> featureEnabledExpTree = 
     Expression.Lambda<Func<string, string, bool>>(body, name, value); 


    // test in isolation 
    var featureEnabledFunc = featureEnabledExpTree.Compile(); 
    bool isMatch1 = featureEnabledFunc("MV", "") 
     && featureEnabledFunc("GAS", "G") || !featureEnabledFunc("GAS", "F"); 

Et puis, si vous avez besoin secondes partie comme un arbre d'expression aussi:

//I want the equal of the following statement in C# Linq Expression 
    Expression<Func<bool>> test = 
     Expression.Lambda<Func<bool>>(
      Expression.OrElse(
       Expression.AndAlso(
        Expression.Invoke(featureEnabledExpTree, 
         Expression.Constant("MV"), 
         Expression.Constant("") 
        ), 
        Expression.Invoke(featureEnabledExpTree, 
         Expression.Constant("GAS"), 
         Expression.Constant("G") 
        ) 
       ), 
       Expression.Not(
        Expression.Invoke(featureEnabledExpTree, 
         Expression.Constant("GAS"), 
         Expression.Constant("F") 
        ) 
       ) 
      ) 
     ); 

    bool isMatch = test.Compile()(); 
+0

Salut Marc, Merci beaucoup. Oui, je dois construire l'expression au moment de l'exécution .. Si possible, s'il vous plaît donnez-moi plus de détails .. –

+0

Je n'ai pas besoin d'avoir si déclaration .. ou partie à évaluer. Je n'ai besoin que de l'expression –

+0

Il n'y a pas d'instruction if. Les OrElse/AndAlso sont juste les C# && et || opérateurs (avec leur stratégie d'évaluation de court-circuit indiquée par les noms dans l'arbre Expression). –

1

comme ça?

Expression<Func<bool>> featureEnabledExpTree =() => 
    IsFeatureEnabled("MV", "") && 
    IsFeatureEnabled("GAS", "G") || 
    !IsFEatureEnabled("GAS", "F"); 
+0

"Cependant, je peux les convertir dynamiquement en fonction de mes notations AST" - ce que j'interprète comme signifiant qu'il doit être construit en fonction des données, donc la capacité du compilateur à traduire C# à des arbres d'expression peut ne pas être utile. –

Questions connexes