我使用Code First EF 5进行MVC4项目。
我有使用公共虚拟ICollection的模型,我想设置这些集合中项目的排序顺序。
例如:
说我有一个订单型号:
public class Order
{
public virtual ICollection<OrderItem> Items { get; set; }
}
和OrderItems模型:
public Class OrderItem
{
public int ID;
public string name;
public decimal price;
}
我想为每个订单设置OrderItem集合的Order,以降序价格出现。我该怎么办呢?或者,事实上,它有可能吗?
我尝试过添加:
this.Items.OrderByDescending(OrderItem,"price");
订单模型构造函数(胖模型,瘦控制器?)
我也尝试将它添加到Controller Action和View中,但没有一个有效。
我猜测在DbContext中可能有某种方法可以做到这一点,但我必须承认我有点迷失。
更新:到目前为止,我已根据建议尝试了以下解决方案,但无济于事。
private ICollection<OrderItem> _Items;
public virtual ICollection<OrderItem> Items
{
get { return _Items.OrderByDescending(item => item.Price).ToList(); }
set { _Items = value; }
}
这产生了这个错误:值不能为空。参数名称:source
我是否需要向构造函数添加内容?
我还尝试在Model和以下内容中添加一个Constructor:
public OrderItem()
{
this.Items = this.Items.OrderByDescending(i => i.Price).ToList();
}
这没有任何效果。
我也尝试过:
this.Items = this.Items.OrderByDescending(OrderItem, "price").ToList();
产生错误&#34; OrderItem是一种类型,但用作变量&#34;。
任何想法的人?
行。我刚刚将它添加到我的控制器中的详细信息方法中:
public ActionResult Details(int id = 0)
{
order.Items = order.Items.OrderByDescending(item => item.price).ToList();
}
哪个有效。我仍然想知道为什么可能获得;组;虽然解决方案不适合将来参考。 Lazy,Eager和Explicit Loading之间的区别是否与此相关?
非常感谢。
好的所以我尝试了Ken4z的建议,并补充道:
public Order()
{
_Items = new List<OrderItem>();
}
这可以防止任何错误,但在控制器中调用操作时实际上不会加载任何项目。可能是一个愚蠢的问题,但无论如何我都要问它:
set { _Items = value; }
是不是构造函数现在将值作为OrderItem列表传递而没有任何内容?试图完全掌握这一点。再次感谢您的帮助。
答案 0 :(得分:2)
var orderedItems = Items.OrderByDescending(item => item.price);
编辑1:
根据David的评论,我正在解释&#34; Set&#34;意思是,您希望Items集合的访问者默认按价格按降序返回。在这种情况下,您需要实现getter。
public class Order
{
private ICollection<OrderItems> _items;
public virtual ICollection<OrderItems> Items
{
get{ return _items.OrderByDescending(item => item.price); }
set{ _items = value; }
}
}
编辑2: 感谢大卫指出错误。
public class Order
{
public Order()
{
_items = new List<OrderItems>();
}
private ICollection<OrderItems> _items;
public virtual ICollection<OrderItems> Items
{
get{ return _items.OrderByDescending(item => item.price).ToList(); }
set{ _items = value; }
}
}
答案 1 :(得分:1)
this.Items.OrderByDescending(OrderItem,"price");
LINQ方法返回一个新实例,因此您必须设置此结果:
this.Items = this.Items.OrderByDescending(OrderItem, "price").ToList();
注意ToList()
,因为结果为IEnumerable<T>
和ICollection<T> : IEnumerable<T>
,但IEnumerable<T>
不属于ICollection<T>
。 List<T> : ICollection<T>
。
您还可以使用“清洁”,类型安全的LINQ方法版本:
this.Items = this.Items.OrderByDescending(i => i.price).ToList();
答案 2 :(得分:0)
如果您最终经常需要排序ICollection导航属性,您可以随时添加如下内容:
[NotMapped]
public IList<OrderItem> ItemsSorted {get {return Items?.OrderBy(p=>p.price).ToList(); }}
到您的域实体,这样当您在控制器或其他代码中使用它时,您不必经常对事物进行排序。