C# 最新高级语法使用示例
本文将展示 C# 最新版本(C# 11 及之前)中的高级语法特性,并提供实际使用示例。这些特性包括模式匹配增强、记录类型、init-only 属性、顶级语句、异步流等现代 C# 功能。
一、模式匹配增强
1.1 类型模式匹配
object obj = "Hello, World!";
if (obj is string str && str.Length > 5)
{
Console.WriteLine($"字符串长度: {str.Length}");
}
else if (obj is int number)
{
Console.WriteLine($"数字: {number}");
}
else
{
Console.WriteLine("未知类型");
}
1.2 关系模式和逻辑模式
int value = 42;
// 使用关系模式
if (value is > 0 and < 100)
{
Console.WriteLine("值在0到100之间");
}
// 使用逻辑模式
if (value is >= 0 or < -10)
{
Console.WriteLine("值大于等于0或小于-10");
}
1.3 转换模式
object obj = 123.45;
if (obj is double d)
{
Console.WriteLine($"双精度值: {d}");
}
else if (obj is not null)
{
Console.WriteLine("不是null,但不是double");
}
二、记录类型(Records)
2.1 不可变数据模型
public record Person(string Name, int Age);
var person1 = new Person("Alice", 30);
var person2 = new Person("Alice", 30);
Console.WriteLine(person1 == person2); // True,值相等
Console.WriteLine(ReferenceEquals(person1, person2)); // False,引用不同
2.2 记录的复制与修改
var person = new Person("Bob", 25);
// 使用with创建副本并修改属性
var updatedPerson = person with { Age = 26 };
Console.WriteLine(updatedPerson); // Person { Name = Bob, Age = 26 }
2.3 位置记录
public record Point(int X, int Y);
var point = new Point(10, 20);
Console.WriteLine(point.X); // 10
Console.WriteLine(point.Y); // 20
三、init-only 属性
3.1 不可变属性
public class Product
{
public string Name { get; init; }
public decimal Price { get; init; }
}
var product = new Product
{
Name = "Laptop",
Price = 999.99m
};
// product.Price = 899.99m; // 编译错误,init-only属性只能在对象初始化时设置
四、顶级语句
4.1 简化程序入口
// 传统方式
class Program
{
static void Main(string[] args)
{
Console.WriteLine("Hello, World!");
}
}
// 使用顶级语句
Console.WriteLine("Hello, World!");
// 可以包含using指令
using System;
Console.WriteLine("Hello, World!");
五、异步流(IAsyncEnumerable)
5.1 异步数据流处理
using System.Collections.Generic;
using System.Threading.Tasks;
async IAsyncEnumerable<int> GenerateNumbersAsync()
{
for (int i = 1; i <= 5; i++)
{
await Task.Delay(500); // 模拟异步操作
yield return i;
}
}
async Task ProcessNumbersAsync()
{
await foreach (var number in GenerateNumbersAsync())
{
Console.WriteLine($"收到数字: {number}");
}
}
六、可空引用类型(Nullable Reference Types)
6.1 明确引用类型是否可为null
#nullable enable
string? nullableString = null; // 允许为null
string nonNullableString = "Hello"; // 不允许为null
// nonNullableString = null; // 编译警告
void PrintName(string name)
{
Console.WriteLine(name.Length); // 如果name为null会警告
}
PrintName(nullableString!); // 使用!告诉编译器"我知道这是非null的"
七、模式匹配增强示例
7.1 复杂对象模式匹配
public abstract record Shape;
public record Circle(double Radius) : Shape;
public record Rectangle(double Width, double Height) : Shape;
Shape shape = new Circle(5);
// 使用switch表达式进行模式匹配
double area = shape switch
{
Circle c => Math.PI * c.Radius * c.Radius,
Rectangle r => r.Width * r.Height,
_ => throw new ArgumentException("未知形状")
};
Console.WriteLine($"面积: {area}");
7.2 属性模式匹配
public record Person(string Name, int Age, string? City);
Person person = new Person("Alice", 30, "New York");
// 使用属性模式匹配
string info = person switch
{
{ Age: > 60 } => "老年人",
{ Age: > 18, City: "New York" } => "纽约成年人",
{ Age: > 18 } => "成年人",
_ => "未成年人"
};
Console.WriteLine(info); // 输出: 纽约成年人
八、记录类型与模式匹配结合
public record Order(int Id, string Product, decimal Price, DateTime Date);
Order order = new Order(1, "Laptop", 999.99m, DateTime.Now);
// 使用with创建修改后的订单
var updatedOrder = order with { Price = 899.99m };
// 使用模式匹配处理不同类型的订单
object orderOrProduct = order;
string description = orderOrProduct switch
{
Order o when o.Price > 500 => $"高价订单 #{o.Id}",
Order o => $"普通订单 #{o.Id}",
_ => "未知对象"
};
Console.WriteLine(description); // 输出: 高价订单 #1
九、顶级语句与异步流结合
#nullable enable
using System;
using System.Threading.Tasks;
// 顶级语句示例
await foreach (var number in GenerateNumbersAsync())
{
Console.WriteLine($"异步数字: {number}");
}
async IAsyncEnumerable<int> GenerateNumbersAsync()
{
for (int i = 1; i <= 3; i++)
{
await Task.Delay(300);
yield return i;
}
}
十、记录类型与可空引用类型
#nullable enable
public record User(string Name, string? Email);
User user1 = new User("Bob", "bob@example.com");
User user2 = new User("Charlie", null); // 允许Email为null
// 使用模式匹配处理可能为null的Email
string emailInfo = user2 switch
{
User u when u.Email != null => $"邮箱: {u.Email}",
User u => "无邮箱信息"
};
Console.WriteLine(emailInfo); // 输出: 无邮箱信息
十一、高级模式匹配示例
11.1 元组模式匹配
var point = (X: 10, Y: 20);
string position = point switch
{
(0, 0) => "原点",
(0, _) => "Y轴上",
(_, 0) => "X轴上",
(x, y) when x > 0 && y > 0 => "第一象限",
(x, y) when x < 0 && y > 0 => "第二象限",
(x, y) when x < 0 && y < 0 => "第三象限",
(x, y) when x > 0 && y < 0 => "第四象限",
_ => "坐标轴上"
};
Console.WriteLine(position); // 输出: 第一象限
11.2 类型测试与转换模式
object obj = "Test";
string result = obj switch
{
string s => $"字符串长度: {s.Length}",
int i when i > 0 => $"正整数: {i}",
int i => $"非正整数: {i}",
null => "null值",
_ => "其他类型"
};
Console.WriteLine(result); // 输出: 字符串长度: 4
十二、记录结构体(Record Structs)
12.1 轻量级不可变数据
public readonly record struct Point(int X, int Y);
Point p1 = new Point(1, 2);
Point p2 = new Point(1, 2);
Console.WriteLine(p1 == p2); // True,值相等
Console.WriteLine(ReferenceEquals(p1, p2)); // False
十三、密封记录(Sealed Records)
public sealed record Person(string Name, int Age)
{
// 不能被继承
}
// public record Employee : Person // 编译错误,Person是密封的
十四、记录工厂方法
public record Product(string Name, decimal Price)
{
public static Product Create(string name, decimal price)
{
return new Product(name, price);
}
}
var product = Product.Create("Laptop", 999.99m);
十五、综合示例:电商订单处理
#nullable enable
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
public record OrderItem(string ProductName, int Quantity, decimal UnitPrice);
public record Order(int Id, string CustomerName, List<OrderItem> Items, DateTime OrderDate);
public class OrderProcessor
{
public async Task ProcessOrdersAsync(IEnumerable<Order?> orders)
{
await foreach (var order in orders.ToAsyncEnumerable())
{
if (order is null) continue;
Console.WriteLine($"处理订单 #{order.Id} - {order.CustomerName}");
var total = order.Items.Sum(i => i.Quantity * i.UnitPrice);
Console.WriteLine($"总金额: {total:C}");
var discounted = order switch
{
{ Items.Count: > 5, OrderDate: >= new DateTime(2023, 1, 1) }
=> total * 0.9m, // 5件以上订单9折
{ Items.Any(i => i.ProductName.Contains("Premium")) }
=> total * 0.95m, // 包含Premium产品95折
_ => total
};
Console.WriteLine($"折扣后金额: {discounted:C}");
}
}
}
// 使用示例
var processor = new OrderProcessor();
var orders = new List<Order?>
{
new Order(1, "Alice", new List<OrderItem>
{
new("Laptop", 1, 999.99m),
new("Mouse", 2, 25.50m)
}, DateTime.Now.AddDays(-1)),
new Order(2, "Bob", new List<OrderItem>
{
new("Premium Headphones", 1, 199.99m),
new("Keyboard", 1, 89.99m)
}, DateTime.Now),
null // 测试null处理
};
await processor.ProcessOrdersAsync(orders.ToAsyncEnumerable());
十六、总结
C# 的最新高级语法特性极大地提升了代码的表达能力和开发效率:
- 模式匹配:使复杂条件逻辑更加清晰和简洁
- 记录类型:简化了不可变数据模型的实现
- init-only 属性:提供了更安全的对象初始化方式
- 顶级语句:简化了小程序的编写
- 异步流:改进了异步数据处理的API
- 可空引用类型:帮助减少空引用异常