null和datetime之间没有隐式转换

时间:2013-12-05 11:27:04

标签: c#

以下代码从给定的DataRow(modelValue)中读取一个数据,并将其解析为nullable DateTime个实例。

问题:请参阅L1 & L2下的代码部分,其中两者在技术上相同(如果我没有发生任何小学生错误)。但是,L1按预期工作,但不是L2。我正在

  

null和datetime之间没有隐式转换

当我执行L2下的代码时。有人可以告诉我吗?

        DateTime? CallBack;

        var callBackDate = modelValue["CallBack"] == DBNull.Value ? null : modelValue["CallBack"].ToString();
        //Parsing
        DateTime cdate;
        if (!DateTime.TryParse(callBackDate, out cdate))
            cdate = DateTime.MinValue;


        //L1
        if (cdate==DateTime.MinValue)
            CallBack = null;
        else
           CallBack = cdate.Date;

       //L2  
       CallBack = cdate == DateTime.MinValue?null:cdate.Date;

4 个答案:

答案 0 :(得分:24)

(Z) ? X : Y

三元运算符要求从第二个操作数(X)到第三个操作数(Y)或从Y到X存在隐式转换。

由于null无法隐式转换为DateTimeDateTime也无法转换为null,因此无法评估表达式。更多相关信息:Type inference woes by Eric Lippert

您必须将null投射到DateTime?。通过这样做,X将是DateTime?类型,Y将是DateTime类型。由于存在从DateTimeDateTime?的隐式转换,因此可以计算表达式,并返回类型为DateTime?的值。

或者,按照相同的逻辑,您也可以将第三个操作数Y转换为DateTime?

答案 1 :(得分:7)

您需要告诉编译器应将null视为DateTime?。否则,编译器不知道null是什么类型。

CallBack = cdate == DateTime.MinValue ? (DateTime?)null : cdate.Date;

答案 2 :(得分:4)

为什么不首先使用支持可空类型的DataRow.Field扩展方法?

DateTime? CallBack = modelValue.Field<DateTime?>("CallBack");

但是因为你实际上有一个string列,所以你需要先解析它:

DateTime? CallBack = null;
string callBackDate = modelValue.Field<string>("CallBack");
if(!string.IsNullOrWhiteSpace(callBackDate))
{
    DateTime cdate;
    if(DateTime.TryParse(callBackDate, out cdate))
        CallBack = cdate;
}

这就是全部。

答案 3 :(得分:1)

您可以执行以下操作:

        DateTime aDateTime = DateTime.MinValue;
        DateTime? aNullableDateTime = aDateTime == DateTime.MinValue ? null : new DateTime?(aDateTime.Date);

使用Nullable(Of T)结构。