11

这失败了There is no implicit conversion between 'null' and 'int'

long? myVar = Int64.Parse( myOtherVar) == 0 ? null : Int64.Parse( myOtherVar);

但是,这成功了:

if( Int64.Parse( myOtherVar) == 0)
    myVar = null;
else
    myVar = Int64.Parse( myOtherVar);

有没有办法让三元运算符成功?

4

5 回答 5

25

编译器在确定右侧的类型时会忽略左侧。所以当它试图推断出

Int64.Parse(myOtherVar) == 0 ? null : Int64.Parse(myOtherVar)

它这样做并没有注意到左侧是 a 的事实long?。为了确定右侧的类型,它指出

Int64.Parse(myOtherVar)

is along并且现在尝试查看nullis 或可以隐式转换为 a long。由于它不能,您会收到您看到的错误消息。

来自 C# 规范的第 7.14 节:

b ? x : y...形式的条件表达式

运算符的第二个和第三个操作数andx控制条件表达式的类型。y?:

(1) If xhas type Xand yhas type Ythen

一种。如果从to存在隐式转换(第 6.1 节) ,但从XtoY不存在,则为条件表达式的类型。YXY

湾。如果从to存在隐式转换(第 6.1 节) ,但从YtoX不存在,则为条件表达式的类型。XYX

C。否则,无法确定表达式类型,并出现编译时错误。

(2) 如果只有一个xandy有一个类型,并且两个xand都y可以隐式转换为那个类型,那么这就是条件表达式的类型。

(3) 否则无法确定表达式类型,出现编译时错误。

请注意,我们处于情况 (2) 中xisnull和没有 type 并且yisInt64.Parse(myOtherVar)并且有 type long。请注意,x它不能隐式转换为y. 因此,(1)和(2)都在上面失败,我们导致(3)导致编译时错误,激发了你的问题。请注意上面的隐含结论,即左侧在确定右侧的类型中没有作用。

纠正这个替换

Int64.Parse(myOtherVar)

(long?)Int64.Parse(myOtherVar)

现在,原因

myVar = null;

可以在 wheremyVar按原样声明,long?因为编译器知道存在从nullto的隐式转换long?

最后,Int64.Parse如果myOtherVar无法解析为long. 请注意,您还执行了两次解析,这是不必要的。更好的模式是

long value;
if(Int64.TryParse(myOtherVar, out value)) {
    myVar = value == 0 ? null : (long?)value;
}
else {
    // handle case where myOtherVar couldn't be parsed
}
于 2010-11-27T05:05:44.313 回答
2

由于三元运算符的最后一部分,您的运算符使用返回一个Int64,而不是一个。nullable如果您这样做,它可能会起作用:

long? myVar = Int64.Parse( myOtherVar) == 0 ? null :
   (long?)Int64.Parse( myOtherVar);

这样您就可以返回 a long?,因此null不需要将其转换为Int64

此外,您在代码中转换了两次值,这是不必要的(一次用于测试,一次用于获取值)。您的代码可能会更好:

long? tempVar = Int64.Parse(myOtherVar);
long? myVar = tempVar==0? null : tempVar;
于 2010-11-27T05:05:42.060 回答
2

我确定你的意思是:

  myVar = value == 0 ? null : (long?)value;

代替

  myVar = value == 0 ? null : value;

我喜欢使用“out”变量。谢谢。

于 2010-11-27T08:51:49.017 回答
0

这将起作用:

long? myVar = (long?)myOtherVar == 0 ? null : (long?)myOtherVar;

..对于那些喜欢简短答案的人。

于 2015-10-07T20:30:41.687 回答
0

编译器尝试从左到右评估表达式

long? myVar = Int64.Parse( myOtherVar) == 0 ? null : Int64.Parse( myOtherVar);

int64.parse方法返回一个long值而不是nullable长值。null所以和之间没有转换Int64.Parse( myOtherVar); 所以,试试这个

long? myVar = Int64.Parse(myOtherVar) == 0 ? (long?) null : Int64.Parse(myOtherVar);

或者
long? myVar = Int64.Parse(myOtherVar) == 0 ? null : (long?) Int64.Parse(myOtherVar);

于 2015-11-20T12:54:55.213 回答