【问题标题】:Ternary Operator behaviour in C#C# 中的三元运算符行为
【发布时间】:2020-02-29 17:40:05
【问题描述】:

我最近遇到了以下代码行。

public class Program
    {      
      public static void Main(string[] args)
        {
          char x = 'X';
           int i = 0;
          Console.WriteLine (true  ? x : 0);
          Console.WriteLine(false ? i : x); 
        }
    }

据我所知,以上代码在这两种情况下都应该输出字符“X”;但是,当我执行代码时,我在控制台中得到了 88;谁能帮我理解为什么输出是 ASCII 码而不是字符?

【问题讨论】:

  • Nitpick:它是“条件运算符”。三元只是意味着有三个操作数

标签: c# .net ascii ternary


【解决方案1】:

三元运算符有自己的类型。这并不总是与您传递给语句的两个操作数的类型相同。相反,它是 两个分支 都可以转换为的类型。在这种情况下,char 隐式转换为int。这意味着三元语句类型是int。请参见下面的示例。 (true ? x : 0).GetType() 语句显示了整个三元语句如何具有int 类型。

public class Program
    {      
      public static void Main(string[] args)
        {
          char x = 'X';
          int i = 0;

          // Prints X fine
          Console.WriteLine(x);

          // Prints System.Int32
          Console.WriteLine((true ? x : 0).GetType());

          // Both print 88 - the int value of 'X'
          Console.WriteLine(true ? x : 0);
          Console.WriteLine(false ? i : x); 
        }
    }

编译器选择int 而不是char 的“原因”有点复杂。 C# spec 定义 char 可隐式转换为 ushortintuintlongfloatdoubledecimal。它还说任何数字类型都可以显式转换为char。这是关键的区别。因为从charint 的转换是隐式(它不需要强制转换),编译器将它用于三元并忽略另一个方向的潜在转换。您可以阅读更多关于确定三元语句类型的规则here

【讨论】:

  • 那你能告诉我为什么 int 没有转换为 char 而不是将 char 转换为 int 吗?
  • @Harry:因为每个char 都可以是int,但不是每个int 都可以是char。一种数据类型大于另一种。
  • @Harry - 两个原因。一 - .NET 更喜欢 int 作为默认数字类型;当需要将两件事转换为通用类型时,大多数时候会选择int。其次 - char 可以很容易地转换为int(实际上,它实际上是伪装的short),但是将int 转换为char 没有多大意义。 123456 是什么字符?
  • @Harry 看到我更新的答案。它是 implicitexplicit 转换之间的区别。三元运算符仅适用于隐式转换。
  • 没有从其他类型到char的隐式转换,正如它所说的here
【解决方案2】:

请注意,'X' 不是string,而是charThe numeric value of which is 88. 这个数值很重要,因为编译器需要理解这个操作:

true ? x : 0

最终,三元条件运算必须产生一个值。直观地说,这个值可能char可能int。对于代码的编译,它不能是一个可能,它必须始终是其中之一。对于编译器来说幸运的是,char 可以直接转换为int。在这种情况下,88

所以操作的结果是int,正在打印到控制台。

【讨论】:

    【解决方案3】:

    这不是三元运算符本身,而是 chars 可以在 c# 中隐式转换为 int,因此,面对具有 int 和 char 并且需要“do if true”和“do if”的三元表达式场景false" 为了保持一致,编译器会将 char 隐式转换为 int。整数不能隐式转换为字符,因此编译器不会走这条路

    int result = bool ? someChar : someInt; 
    
    char result = bool ? (char)someInt : someChar;
    

    这些都可以;一个使用 someChar 到 int 的隐式转换来实现三元的一致性(consistent int),另一个使用 someInt 到 char 的显式转换来实现一致的 char

    第一个将导致(在您的情况下打印)一个 int,第二个将导致一个 char。你也可以玩这个:

    int result = bool ? (char)someInt : someChar;
    

    将int显式转换为char,三进制结果为char,存储在result中时隐式转换为int..

    X 的 ascii 代码是 88

    【讨论】:

      猜你喜欢
      • 2023-03-09
      • 2021-09-09
      • 1970-01-01
      • 2012-04-02
      • 1970-01-01
      • 2018-09-18
      • 2011-02-15
      • 2021-10-25
      相关资源
      最近更新 更多