【问题标题】:5* difficulty C# LINQ expression for generic class's property通用类属性的 5* 难度 C# LINQ 表达式
【发布时间】:2022-09-30 20:30:26
【问题描述】:

干杯,我正在尝试创建通用功能返回动态 LINQ 表达式如下。

// creating baseClassInstance...
var baseClassInstance = new BaseClass<GenericClass>(new GenericClass(true));

// getting expression, func, and finally the field\'s value
var expression = GetBoolEqualsExpression<GenericClass>(\"SomeBool\");
var func = expression.Compile();
var result = func.Invoke(baseClassInstance);

public class BaseClass<T>
{
    public T GenericInstance;
    public BaseClass(T genericInstance)
    {
        this.GenericInstance = genericInstance;
    }
}

public class GenericClass
{
    public bool? SomeBool;
    public GenericClass(bool someBool)
    {
        this.SomeBool = someBool;
    }
}

目前我面临的问题是GetBoolEqualsExpression

    private System.Linq.Expressions.Expression<Func<BaseClass<Tgeneric>, bool>> GetBoolEqualsExpression<Tgeneric>(string propertyName) where Tgeneric : class
    {
        var parameter = System.Linq.Expressions.Expression.Parameter(typeof(BaseClass<Tgeneric>), propertyName);
        var property = System.Linq.Expressions.Expression.Field(parameter, propertyName);
        var target = System.Linq.Expressions.Expression.Constant(true);

        var expConverted = System.Linq.Expressions.Expression.Convert(property, typeof(bool));
        var exp = System.Linq.Expressions.Expression.Call(expConverted, \"Equals\", null, target);
        var lambda = System.Linq.Expressions.Expression.Lambda<Func<BaseClass<Tgeneric>, bool>>(exp, parameter);

        return lambda;
    }

如果我将第一行保留为Parameter(typeof(BaseClass&lt;Tgeneric&gt;)...,那么带有property 的第二行将失败

System.ArgumentException: Instance field \'SomeBool\' is not defined for type \'BaseClass`1[GenericClass]\'

如果我更改为Parameter(typeof(Tgeneric)...,那么lambda 的第 7 行将失败

System.ArgumentException: \'ParameterExpression of type \'GenericClass\' cannot be used for delegate parameter of type \'BaseClass`1[GenericClass]\'\'

任何帮助都非常感谢!

  • 第二个错误。您不能将继承的类强制转换为基类。所以将 Func<BaseClass<Tgeneric>> 更改为 Func<Tgeneric>

标签: c# linq expression


【解决方案1】:

您忘记访问BaseClassGenericInstance 字段。

这条线不起作用,因为parameterBaseClass&lt;GenericClass&gt;,而不是GenericClass

var property = System.Linq.Expressions.Expression.Field(parameter, propertyName);

给定一个名为BaseClass&lt;GenericClass&gt;parameter,您通常如何访问SomeBool?你会做parameter.GenericInstance.SomeBool,对吧?不是parameter.SomeBool 本身。

所以用表达式树做类似的事情:

var genericInstance = Expression.Field(parameter, "GenericInstance");
var property = Expression.Field(genericInstance, propertyName);

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-07-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多