差别
这里会显示出您选择的修订版和当前版本之间的差别。
| 两侧同时换到之前的修订记录 前一修订版 后一修订版 | 前一修订版 | ||
| csharp:运算符 [2025/11/21 10:50] – [2. ?? 运算符 (双问号)] 张叶安 | csharp:运算符 [2025/12/22 11:37] (当前版本) – 张叶安 | ||
|---|---|---|---|
| 行 145: | 行 145: | ||
| </ | </ | ||
| - | ===== 8. ? 与 ?? (Null 处理与条件逻辑) ===== | ||
| - | 在 C# 中,`?` 和 `??` 运算符主要用于处理 **null 值(空值)** 以及 **条件逻辑**。它们不仅能简化代码,还能显著提高代码的可读性和安全性(防止空引用异常)。 | + | ===== 9. 综合总结表 ===== |
| - | + | ||
| - | ==== 8.1. ? 运算符 (单问号) | + | |
| - | + | ||
| - | `?` 符号在 C# 中有三种截然不同的用法,取决于上下文。 | + | |
| - | + | ||
| - | === 8.1.1 可空类型修饰符 (Nullable Type Modifier) === | + | |
| - | 用于定义一个**值类型**(如 `int`, `double`, `bool`, `DateTime` 等)可以存储 `null`。 | + | |
| - | + | ||
| - | * **原理**:`int? | + | |
| - | * **场景**:数据库中的数字字段可能为空,或者需要表示“未设置”的状态。 | + | |
| - | + | ||
| - | <code csharp> | + | |
| - | int a = 10; // 正常 int,不能赋值 null | + | |
| - | int? b = null; // 可空 int,可以赋值 null | + | |
| - | + | ||
| - | if (b.HasValue) | + | |
| - | { | + | |
| - | Console.WriteLine(b.Value); | + | |
| - | } | + | |
| - | </ | + | |
| - | + | ||
| - | === 8.1.2 三元条件运算符 (Ternary Conditional Operator) === | + | |
| - | 这是 `if-else` 语句的简写形式,用于根据布尔表达式返回两个值中的一个。 | + | |
| - | + | ||
| - | * **语法**:`condition ? true_value : false_value` | + | |
| - | * **含义**:如果条件为真,返回冒号左边的值;否则返回冒号右边的值。 | + | |
| - | + | ||
| - | <code csharp> | + | |
| - | int x = 10; | + | |
| - | string result = (x > 5) ? " | + | |
| - | </ | + | |
| - | + | ||
| - | === 8.1.3 Null 条件运算符 (Null-conditional Operator) === | + | |
| - | //(C# 6.0+)// 也称为“安全导航运算符”。用于在访问成员(属性、方法)或索引器之前检查对象是否为 `null`。 | + | |
| - | + | ||
| - | * **语法**:`obj? | + | |
| - | * **含义**:如果对象不为 `null`,则访问成员;如果对象为 `null`,则整个表达式直接返回 `null`,而**不会**抛出 `NullReferenceException`。 | + | |
| - | + | ||
| - | <code csharp> | + | |
| - | string text = null; | + | |
| - | // length 将会是 null (int? | + | |
| - | int? length = text? | + | |
| - | + | ||
| - | // 链式调用 | + | |
| - | Person person = null; | + | |
| - | string city = person? | + | |
| - | </ | + | |
| - | + | ||
| - | ==== 8.2. ?? 运算符 (双问号) ==== | + | |
| - | + | ||
| - | `??` 系列运算符主要用于处理 null 时的默认值逻辑。 | + | |
| - | + | ||
| - | ==== 2.1 Null 合并运算符 (Null-coalescing Operator) ==== | + | |
| - | 用于判断左侧的操作数是否为 `null`。 | + | |
| - | + | ||
| - | * **语法**:`left ?? right` | + | |
| - | * **含义**:如果 `left` **不为** `null`,则返回 `left`;如果 `left` **为** `null`,则返回 `right`。 | + | |
| - | + | ||
| - | <code csharp> | + | |
| - | string input = null; | + | |
| - | // 如果 input 是 null,则 name 变成 " | + | |
| - | string name = input ?? " | + | |
| - | </ | + | |
| - | + | ||
| - | ==== 2.2 Null 合并赋值运算符 (Null-coalescing Assignment Operator) ==== | + | |
| - | //(C# 8.0+)// 这是 `??` 和 `=` 的组合。 | + | |
| - | + | ||
| - | * **语法**:`variable ??= value` | + | |
| - | * **含义**:只有当左侧变量 `variable` 为 `null` 时,才将右侧的 `value` 赋值给它。如果左侧不为 null,则保持原值不变。 | + | |
| - | + | ||
| - | <code csharp> | + | |
| - | List< | + | |
| - | + | ||
| - | // 因为 numbers 是 null,所以会初始化新列表 | + | |
| - | numbers ??= new List< | + | |
| - | + | ||
| - | // 此时 numbers 已不是 null,这行代码不会执行任何操作 | + | |
| - | numbers ??= new List< | + | |
| - | </ | + | |
| - | + | ||
| - | ===== 3. 综合代码示例 ===== | + | |
| - | + | ||
| - | 以下示例展示了如何在一个场景中混合使用上述运算符。 | + | |
| - | + | ||
| - | <code csharp> | + | |
| - | using System; | + | |
| - | using System.Collections.Generic; | + | |
| - | + | ||
| - | public class Program | + | |
| - | { | + | |
| - | public static void Main() | + | |
| - | { | + | |
| - | // 1. 可空类型修饰符 (?) | + | |
| - | int? nullableInt = null; | + | |
| - | + | ||
| - | // 2. Null 合并运算符 (??) | + | |
| - | // 如果 nullableInt 是 null,则使用默认值 0 | + | |
| - | int finalValue = nullableInt ?? 0; | + | |
| - | Console.WriteLine($" | + | |
| - | + | ||
| - | // 3. 三元运算符 (?:) | + | |
| - | string status = (finalValue > 5) ? " | + | |
| - | Console.WriteLine($" | + | |
| - | + | ||
| - | // 4. Null 条件运算符 (?.) | + | |
| - | Person person = null; | + | |
| - | // 如果 person 为 null,name 直接为 null,不会报错 | + | |
| - | string name = person? | + | |
| - | Console.WriteLine($" | + | |
| - | + | ||
| - | // 组合使用:安全访问 + 默认值 | + | |
| - | // 如果 person 为 null 或者 Name 为 null,则显示 " | + | |
| - | string displayName = person? | + | |
| - | Console.WriteLine($" | + | |
| - | + | ||
| - | // 5. Null 合并赋值运算符 (??=) | + | |
| - | List< | + | |
| - | + | ||
| - | // 因为 tags 是 null,所以进行赋值 | + | |
| - | tags ??= new List< | + | |
| - | tags.Add(" | + | |
| - | + | ||
| - | Console.WriteLine($" | + | |
| - | } | + | |
| - | } | + | |
| - | + | ||
| - | public class Person | + | |
| - | { | + | |
| - | public string Name { get; set; } | + | |
| - | } | + | |
| - | </ | + | |
| - | + | ||
| - | ===== 4. 总结表 ===== | + | |
| - | + | ||
| - | ^ 运算符 ^ 名称 ^ 语法示例 ^ 解释 ^ | + | |
| - | | **`?`** | 可空类型修饰符 | `int? x` | 允许值类型为 null。 | | + | |
| - | | **`?:`** | 三元运算符 | `a ? b : c` | 如果 a 为真选 b,否则选 c。 | | + | |
| - | | **`?.`** | Null 条件运算符 | `obj?.Prop` | 如果 obj 非空则访问 Prop,否则返回 null。 | | + | |
| - | | **`??`** | Null 合并运算符 | `a ?? b` | 如果 a 非空返回 a,否则返回 b (默认值)。 | | + | |
| - | | **`??=`** | Null 合并赋值 | `a ??= b` | 仅当 a 为 null 时,将 b 赋值给 a。 | | + | |
| - | + | ||
| - | + | ||
| - | ===== 8. 综合总结表 ===== | + | |
| ^ 类别 ^ 常用运算符 ^ 关键点 ^ | ^ 类别 ^ 常用运算符 ^ 关键点 ^ | ||