我正在尝试对可能处于以下(推断)状态之一的数据进行排序(按此顺序):
live
(有效StartDate
,null EndDate
); draft
(null StartDate
); ended
(有效EndDate
)。我在IQueryable
上继承了以下语法:
iQueryableData
.OrderBy(t => t.StartDate == null ? 1 : (t.EndDate == null ? 0 : 2))
.ThenByDescending(t => t.StartDate)
.ThenBy(t => t.PartnerId)
这很好,因为它根据一些IF
语句对表格的前3列中的一列进行排序。
现在我需要在不同(但相似)的模型上重写它以在内存中工作(所以只是LINQ
,而不是IQueryable
)。以下是上述查询将粗略转换为:
data
.OrderBy(t => t.StartDate == null
? t.EndDate // DateTime
: (t.EndDate == null
? t.Id // integer
: t.Name // string
)
)
这显然无法编译,因为
CS0173 C#无法确定条件表达式的类型,因为 'int'和'string'之间没有隐式转换
据推测,我可以按整数排序,但是我不知道在这种情况下数字会引用什么(在类中写入的属性的顺序?按照同名的顺序排序? )。
不幸的是,我发现的与我有关的所有问题都是基于IF
语句进行排序,该语句依赖于外部值(不在数据内部)。
答案 0 :(得分:1)
使用ThenBy扩展程序。这可确保在应用新订单标准时维护先前的订单。对于每个特定情况,返回所需的属性以参与顺序(Name,Id,EndDate),以便集合中的每个组将按这些值排序。对不符合原始条件的其他项使用一些常量值,以便当前的ThenBy保持其顺序不变。
items
//sort by live, draft and ended
.OrderBy(t => t.StartDate == null ? 1 : (t.EndDate == null ? 0 : 2))
//keep the live, draft and ended sort,
//and for the live items apply only a sort by ID,
//but let the other items in the previous order (live, draft and ended)
//by returning the same value for each (zero or null)
.ThenBy( t=> t.StartDate != null && t.EndDate == null ? t.ID : 0)
//the same
//keep the sort by live, draft, ended and now by ID for live ones only
//but for the draft items sort them by EndDate
//leave the others unaffected by this sort
.ThenBy( t=> t.StartDate == null && t.EndDate != null ? t.EndDate : default(DateTime?))
//same - sort ended items by name
.ThenBy( t=> t.StartDate != null && t.EndDate != null ? t.Name : null)
答案 1 :(得分:0)
我建议你为你的数据实现一个比较器。 compareTo方法将处理您可能遇到的一些复杂情况:如果linq必须比较Date,Number或String,该怎么办?