在处理Nullable类型时在LinQ中使用.HasValue(),有没有办法摆脱“可能的SystemInvalidException”?
我有一个列表Foo's
。在处理Nullable类型时在LinQ中使用.HasValue(),有没有办法摆脱“可能的SystemInvalidException”?
Foo
有型DateTime?
的CreateDate
我想要得到的最古老的Foo
。我用直观的方式尝试,但我得到了一个可能的System.InvalidOperationException
。
DateTime oldestFoo =
(from f in allFoos where f.CreateDate.HasValue select f.CreateDate.Value).Min();
有什么我错过了,或者它只是不可能这样吗?
我可以用LinQ这样做,但我也想学习其他方法。
DateTime oldestFoo = DateTime.MaxValue;
foreach (var foo in allFoos)
{
if (foo.CreateDate.HasValue && oldestFoo > foo.CreateDate)
{
oldestFoo = (DateTime)foo.CreateDate;
}
}
万一你“重新仍然坚持,你可能要考虑使用DefaultIfEmpty
- 看看这可以帮助:
DateTime oldestFoo = allFoos.Where(f => f.CreateDate.HasValue)
.Select(f => f.CreateDate.Value)
.DefaultIfEmpty(DateTime.MaxValue)
.Min();
我不认为你要使用GetValueOrDefault
之内,否则如果第一个查询完全没有返回结果,您将会仍然有问题。
可以使用GetValueOrDefault
方法,该方法不会引起异常,并且有在这一点上没有空值,结果是一样的:
DateTime oldestFoo = (
from f in allFoos
where f.CreateDate.HasValue
select f.CreateDate.GetValueOrDefault()
).Min();
你也可以放心,在这种情况下演员阵容不会失败吗? 'select(DateTime)f.CreateDate',因为你已经通过'HasValue'确保它有一个值。 – dwerner 2012-03-19 15:42:33
@dwerner:即使您知道在那一点上没有空值,编译器也不知道这一点。它没有对代码进行足够的分析,以认识到'HasValue'条件在代码的另一部分中清除了空值。 – Guffa 2012-03-19 15:45:41
用GetValueOrDefault(DateTime.MaxValue)编辑它,我认为是正确的? – radbyx 2012-03-19 15:46:43
DateTime oldestFoo =
(from f in allFoos select f.CreateDate).Min() ?? DateTime.MaxValue;
或者稍微更简洁:
DateTime oldestFoo =
allFoos.Select(f => f.CreateDate).Min() ?? DateTime.MaxValue;
我的建议是不调用Min
前项目DateTime?
到DateTime
。
这里有一个Nullable<int>
样品,做不项目int
来说明Min
和Max
附加功能如何与可空INT的空和不同的名单的行为。
var foo = Enumerable.Empty<int?>();
Console.WriteLine(foo.Min());
foo = new int? [] { null, -20, 10 };
Console.WriteLine(foo.Min());
Console.WriteLine(foo.Max());
的上述的输出是:
null
-20
10
代替在FOOS列表过滤DateTime?
实例只有那些具有值,允许Min
延伸到与DateTime?
值工作,而不是投射到DateTime
。当你有一个空的列表(如上面的例子),你会从Min
而不是InvalidOperationException
得到一个null
值。
当没有任何值的结果时,你想要结果是什么? (一个简短但完整的程序会在这里帮助...) – 2012-03-19 15:38:52
如果没有,最老的可以是DateTime.MaxValue。 – radbyx 2012-03-19 15:40:29
我的观点是:你如何期望'Min()'知道? – 2012-03-19 15:41:41