C#:按可为空的DateTime属性对对象列表进行排序
我有一个对象列表:C#:按可为空的DateTime属性对对象列表进行排序,c#,linq,C#,Linq,我有一个对象列表:List List=… 每个对象都有一个DateTime属性,我们称之为“Date” 我想按此日期属性降序排列此列表。然而,当我尝试 list.Sort(新比较((x,y)=>DateTime.Compare(x.Date,y.Date))) 它会抱怨,因为Date属性可以为空 如何对列表进行排序,将可为空的日期视为最大日期,使其显示在顶部?对我来说,快速简单的替代方法是不使日期字段为空,但让我们假设现在不允许这样做 简而言之:如果DateTime可以为空,如何按DateTim
List List=…
每个对象都有一个DateTime属性,我们称之为“Date”
我想按此日期属性降序排列此列表。然而,当我尝试
list.Sort(新比较((x,y)=>DateTime.Compare(x.Date,y.Date)))
它会抱怨,因为Date属性可以为空
如何对列表进行排序,将可为空的日期视为最大日期,使其显示在顶部?对我来说,快速简单的替代方法是不使日期字段为空,但让我们假设现在不允许这样做
简而言之:如果DateTime可以为空,如何按DateTime对对象列表排序?一种可能的方法可能是:
list.Sort(new Comparison<FakeObject>((x, y) =>
-DateTime.Compare(x.Date ?? DateTime.MaxValue,
y.Date ?? DateTime.MaxValue)));
list.Sort(新比较((x,y)=>
-DateTime.Compare(x.Date×DateTime.MaxValue,
y、 日期??DateTime.MaxValue));
更新:修改为在OP编辑问题进行澄清后使用MaxDate
请注意,您可以采用任何一种方式(
MinDate
或MaxDate
)进行此操作。底线是这样的,如果它是空的,那么给它一些静态值来完成你想要的。如果你想把所有空日期转换成最大日期值,那么就在你的函数中这样做。您可以使用null coalesce运算符来获得更简洁的语法:
list.Sort((x, y) =>
DateTime.Compare(x.Date ?? DateTime.MaxValue, y.Date ?? DateTime.MaxValue))
在比较之前,将null date实例设置为MAX怎么样
list.ForEach(x => x.Date = x.Date ?? null : DateTime.Max : x.Date);
…之后是对比较的调用。如果可以替换列表,而不是就地修改列表,则可以使用LINQ
list = list.OrderByDescending(x => x.Date ?? DateTime.MaxValue).ToList();
我会这样做 首先,给我们上这样的课
class Widget
{
public DateTime? DateCreated { get ; set ; }
}
我会编写一个自定义比较器,类似这样:
class Widget
{
public DateTime? DateCreated { get ; set ; }
}
class WidgetComparer : IComparer<Widget> , IComparer<DateTime?>
{
public bool NullCollatesHigh { get ; private set ; }
private WidgetComparer( bool nullCollatesHigh )
{
this.NullCollatesHigh = nullCollatesHigh ;
return ;
}
public int Compare( Widget x , Widget y )
{
int cc ;
if ( x == null && y == null ) cc = 0 ;
else if ( x != null && y != null ) cc = Compare( x.DateCreated , y.DateCreated ) ;
else if ( NullCollatesHigh ) cc = x == null ? +1 : -1 ;
else cc = x == null ? -1 : +1 ;
return cc ;
}
public int Compare(DateTime? x, DateTime? y)
{
int cc ;
if ( x == null && y == null ) cc = 0 ;
else if ( x != null && y != null ) cc = DateTime.Compare( x.Value , y.Value ) ;
else if ( NullCollatesHigh ) cc = x == null ? +1 : -1 ;
else cc = x == null ? -1 : +1 ;
return cc ;
}
}
其中,
true
指定将空值整理得比任何其他值都高,false
指定将空值整理得比任何值都低。+1我的朋友,我很高兴我的答案模仿了你的答案,这让我感到谦卑!这会使列表中的值发生变化,这似乎是不可取的,他只是想在排序时将其用作有效值。啊。。是的,很公平!这也会按降序排列日期?@HenleyChiu,不,这不会排序DESC
。要做到这一点,只需在末尾添加一个调用Reverse
。将排序
降序会更有效:要么交换x
和y
,要么在日期时间前面放一个-
(或者-1*
,如果你觉得更清楚的话)。比较。(同样,正如所写,它不编译。Sort
返回void
,而不是列表)@TimS.,现在这是一个有趣的方法。请验证我的编辑是否正确。我已经选择了一个答案。。。它只有一行,比你的简单多了。谢谢
widgetList.Sort( new WidgetComparer( true/false ) ) ;