2016-02-19 1 views
0

J'ai récemment rencontré un problème concernant la contravariance des paramètres d'une fonction dans C#, et comment cela n'est pas respecté dès qu'une expression est enroulée autour de cette fonction. Voici un exemple de ce dont je parle:Dans l'expression <TDelegate>, les paramètres de TDelegate ne sont pas contravariant, façons de contourner?

class BaseClass 
{ 
    public bool IsSomething() 
    { 
     return true; 
    } 
} 

class SubClass : BaseClass { } 

static void Main(string[] args) 
{ 
    // This works totally fine 
    Func<BaseClass, bool> funcWithBaseClass = item => item.IsSomething(); 
    Func<SubClass, bool> funcWithSuperClass = funcWithBaseClass; 
    var aValidCast = (Func<SubClass, bool>)funcWithBaseClass; 

    Expression<Func<BaseClass, bool>> expressionWithBaseClass = item => item.IsSomething(); 
    // Expression<Func<SubClass, bool>> expressionWithSubClass = expressionWithBaseClass; Get a type mismatch error 
    // var invalidCast = (Expression<Func<SubClass, bool>>)expressionWithBaseClass; Invalid cast exception 
} 

Je figure la question doit provenir du fait que maintenant le Func a lui-même devenir un paramètre de type générique.

Est-ce que quelqu'un sait comment je pourrais éventuellement contourner ce comportement?

+2

'' expression est une classe ** **, et les classes ne supportent pas co/variance contre. –

Répondre

0

J'ai trouvé un moyen de contourner cela, si quelqu'un est curieux. J'ai simplement fait quelque chose comme ceci:

public static Expression<Func<SubClass,bool>> ConvertExpression(Expression<Func<BaseClass, bool>> baseClassExpression) 
{ 
    Func<SubClass, bool> filterFunction = baseClassExpression.Compile(); // This assignment works because Func parameter types are contravariant. 
    Expression<Func<SubClass, bool>> filterExpression = item => filterFunction(item); 

    return filterExpression; 
}