实体框架通用

本文关键字:框架 实体 | 更新日期: 2023-09-27 18:29:38

我有如下代码:

switch(sort.Column)
{
  case "code":
    model = (sort.Direction == SortDirection.Ascending)
            ? model.OrderBy(x => x.code)
            : model.OrderByDescending(x => x.code);
    break;
  case "name":
    model = (sort.Direction == SortDirection.Ascending)
            ? model.OrderBy(x => x.name)
            : model.OrderByDescending(x => x.name);
    break;
..............
}

我有大约10-15个字段(如"代码"answers"名称"),我不想复制和粘贴只有一个不同的类似代码-字段名称。

是否有某种方法可以概括查询?

实体框架通用

您可以使用反射(这假设codename是属性;如果它们是公共变量,则必须进行相应的修改):

model = (sort.Direction == SortDirection.Ascending)
  ? model.OrderBy( x => x.GetType()
      .GetProperty( sort.Column ).GetValue( x, null ) ) :
  : model.OrderByDescending( x => x.GetType()
      .GetProperty( sort.Column ).GetValue( x, null ) );

正如Dunc在下面的评论中指出的那样,这种方法在枚举的每一步都强制进行反射,并且随着操作的进行,反射是昂贵的。如果集合是同构的,则可以通过将反射移出枚举来获得更好的性能。如果您的model只包含类型为Foo元素,则可以执行以下操作:

var prop = typeof( Foo ).GetProperty( sort.Column );
model = (sort.Direction == SortDirection.Ascending)
  ? model.OrderBy( x => prop.GetValue( x, null ) ) :
  : model.OrderByDescending( x => prop.GetValue( x, null ) );

如果您的集合不是同质的,请不要这样做会抛出TargetException

这会让您开始,但如果属性和列完全匹配,您也可以使用反射通过Column获取属性名称。

// inline function
Func<Func<Model, TResult>, Model> Order = criteria => 
{
    return (sort.Direction == SortDirection.Ascending)
            ? model.OrderBy(criteria)
            : model.OrderByDescending(criteria);
}
... code down to switch ...

这会将您的姓名大小写缩短为:

model = Order(x => x.name);

但有了反思,你可以不用开关就可以做到,但我的反思能力有点弱,所以如果其他人愿意,我会把它留给他们。

正如"没有这样的IP"所说,这有一些模式-命令调度器/工厂方法等。这些都是有效的选择。但有时这些只是掩盖了复杂性。我的建议是考虑使用动态linq。这里有一个链接可以让你开始:http://weblogs.asp.net/scottgu/archive/2008/01/07/dynamic-linq-part-1-using-the-linq-dynamic-query-library.aspx

如果你愿意,你也可以自己滚动,因为它并不太复杂。创建您自己的扩展方法,允许您传递有关您的顺序的参数(即排序方向、排序列),在该扩展方法中,使用system.linq.expressions命名空间通过语句建立您自己的顺序。以下也是一个例子:http://ronniediaz.com/2011/05/24/orderby-string-in-linq-c-net-dynamic-sorting-of-anonymous-types/