C# 7.0在原有语言基础上新增了多项实用特性,这些特性能从不同维度优化代码编写效率,不过每个特性都有对应的使用规则和需要注意的细节,下面逐一介绍核心要点。

out变量声明的简化
在C# 7.0之前,使用out参数需要先单独声明变量,再传入方法,C# 7.0支持在方法调用时直接声明out变量,不需要提前定义。使用这个特性时要注意,声明的out变量作用域是包含它的整个代码块,不是仅在方法调用处有效。
// 旧写法
int oldValue;
if (int.TryParse("123", out oldValue))
{
Console.WriteLine(oldValue);
}
// C# 7.0新写法
if (int.TryParse("123", out int newValue))
{
Console.WriteLine(newValue);
}
// newValue在这里仍然可以访问
Console.WriteLine(newValue * 2);
元组的支持
C# 7.0引入了原生元组类型,不需要再依赖Tuple类,语法更简洁。使用时需要注意,元组默认的元素名称是Item1、Item2这样的格式,如果要自定义名称,需要在声明时显式指定,另外元组是值类型,赋值时会进行值拷贝,不是引用传递。
// 声明带自定义名称的元组
var user = (Id: 1, Name: "张三", Age: 25);
Console.WriteLine($"用户ID:{user.Id},姓名:{user.Name}");
// 元组解构
(int userId, string userName, int userAge) = user;
Console.WriteLine($"解构后姓名:{userName}");
// 元组作为返回值
static (int, string) GetUserInfo()
{
return (2, "李四");
}
模式匹配
C# 7.0新增了is模式匹配和switch模式匹配,可以在类型判断的同时完成变量声明,不需要额外的类型转换。使用switch模式匹配时要注意,case的顺序是有意义的,更具体的匹配条件要放在前面,否则会被前面的条件覆盖。
object obj = 100;
// is模式匹配
if (obj is int num)
{
Console.WriteLine($"obj是整数,值为{num}");
}
// switch模式匹配
switch (obj)
{
case string s:
Console.WriteLine($"obj是字符串,值为{s}");
break;
case int i when i > 50:
Console.WriteLine($"obj是大于50的整数,值为{i}");
break;
case int i:
Console.WriteLine($"obj是小于等于50的整数,值为{i}");
break;
default:
Console.WriteLine("obj是其他类型");
break;
}
本地函数
本地函数是定义在另一个函数内部的函数,只能在外层函数内部被调用,作用域仅限于外层函数。使用本地函数时要注意,它可以访问外层函数的变量,但是如果本地函数使用了外层函数的变量,外层函数的变量生命周期会被延长到本地函数执行结束之后。
static void OuterMethod()
{
int count = 0;
// 本地函数
void InnerMethod()
{
count++;
Console.WriteLine($"内部函数调用,count值为{count}");
}
InnerMethod();
InnerMethod();
}
// 调用外层函数
OuterMethod();
更多实用小特性
数字分隔符
可以在数字中插入下划线作为分隔符,提升大数字的可读性,下划线可以放在任意数字之间,不影响数值本身,但是不能放在数字的开头或结尾,也不能放在小数点旁边。
int bigNum = 1_000_000;
double pi = 3.14_15_92;
Console.WriteLine($"大数字:{bigNum},圆周率:{pi}");
ref返回和ref本地变量
C# 7.0支持方法返回ref引用,也可以声明ref本地变量指向某个变量的引用,修改ref变量会直接修改原变量的值。使用时要注意,ref返回不能返回局部变量的引用,因为局部变量在方法结束后会被销毁,返回它的引用会导致访问违规。
static ref int GetFirstElement(int[] arr)
{
// 不能返回局部变量的ref,这里返回数组第一个元素的ref是合法的
return ref arr[0];
}
int[] nums = { 1, 2, 3 };
ref int first = ref GetFirstElement(nums);
first = 100;
Console.WriteLine(nums[0]); // 输出100
常见注意事项总结
- 使用元组时不要过度嵌套,否则会降低代码的可读性,复杂结构建议使用自定义类代替。
- 模式匹配的
switch语句中,case条件要从具体到模糊排列,避免逻辑错误。 - 本地函数如果不需要访问外层变量,尽量不依赖外层变量,减少耦合。
- ref返回只能返回数组元素、对象的字段或属性等生命周期足够的存储位置的引用,不能返回局部变量。