Alf*_*ono 21 c# linq entity-framework-5
鉴于原始值,age我知道如何创建这样的表达式:
//assuming: age is an int or some other primitive type
employee => employee.Age == age
Run Code Online (Sandbox Code Playgroud)
通过做这个:
var entityType = typeof(Employee);
var propertyName = "Age";
int age = 30;
var parameter = Expression.Parameter(entityType, "entity");
var lambda = Expression.Lambda(
Expression.Equal(
Expression.Property(parameter, propertyName),
Expression.Constant(age)
)
, parameter);
Run Code Online (Sandbox Code Playgroud)
除了在有问题的属性和常量不是原始类型的情况下,这种方法很好.
如果比较是在对象之间,我将如何构造一个类似的表达式?
使用EF我可以写:
Location location = GetCurrentLocation();
employees = DataContext.Employees.Where(e => e.Location == location);
Run Code Online (Sandbox Code Playgroud)
这也有效,但如果我尝试创建相同的表达式:
var entityType = typeof(Employee);
var propertyName = "Location";
var location = GetCurrentLocation();
var parameter = Expression.Parameter(entityType, "entity");
var lambda = Expression.Lambda(
Expression.Equal(
Expression.Property(parameter, propertyName),
Expression.Constant(location)
)
, parameter);
Run Code Online (Sandbox Code Playgroud)
我收到一条错误消息:
Unable to create a constant value of type 'Location'. Only primitive types or enumeration types are supported in this context.
我的怀疑是Expression.Constant()只需要原始类型,所以我需要使用不同的表达式工厂方法.(maype Expression.Object? - 我知道不存在)
有没有办法创建一个比较对象的表达式?为什么EF能够在编译LINQ语句时正确解释它,但是当它是表达式时却不能解释它?
除了之前的答案中提到的内容.更具体的解决方案将如下:
public static Expression CreateExpression<T>(string propertyName, object valueToCompare)
{
// get the type of entity
var entityType = typeof(T);
// get the type of the value object
var valueType = valueToCompare.GetType();
var entityProperty = entityType.GetProperty(propertyName);
var propertyType = entityProperty.PropertyType;
// Expression: "entity"
var parameter = Expression.Parameter(entityType, "entity");
// check if the property type is a value type
// only value types work
if (propertyType.IsValueType || propertyType.Equals(typeof(string)))
{
// Expression: entity.Property == value
return Expression.Equal(
Expression.Property(parameter, entityProperty),
Expression.Constant(valueToCompare)
);
}
// if not, then use the key
else
{
// get the key property
var keyProperty = propertyType.GetProperties().FirstOrDefault(p => p.GetCustomAttributes(typeof(KeyAttribute), false).Length > 0);
// Expression: entity.Property.Key == value.Key
return Expression.Equal(
Expression.Property(
Expression.Property(parameter, entityProperty),
keyProperty
),
Expression.Constant(
keyProperty.GetValue(valueToCompare),
keyProperty.PropertyType
)
);
}
}
Run Code Online (Sandbox Code Playgroud)
重要要点:
propertyType并且valueType兼容(它们是相同类型或可转换)KeyAttribute)希望有所帮助.
| 归档时间: |
|
| 查看次数: |
16405 次 |
| 最近记录: |