C# 10新增功能_C# 10新增特性

2022/2/6 14:13:06

本文主要是介绍C# 10新增功能_C# 10新增特性,对大家解决编程问题具有一定的参考价值,需要的程序猿们随着小编来一起学习吧!

C# 10新增功能_C# 10新增特性_语法方面的变更

一、C# 10 向 C# 语言添加了以下功能和增强功能:

记录结构
结构类型的改进
内插字符串处理程序
指令
文件范围的命名空间声明
扩展属性模式
对 Lambda 表达式的改进
可使用 内插字符串
记录类型可密封
改进型明确赋值
在同一析构中可同时进行赋值和声明
可在方法上使用 属性
CallerArgumentExpression 属性
增强的 pragma

更多详细点击参考:

C# 10 中的新增功能 - C# 指南 | Microsoft Docs

二、struct 增加语法

record struct

首先自然是 record struct,解决了 record 只能给 class 而不能给 struct 用的问题:

record struct Point(int X, int Y);

用 record 定义 struct 的好处其实有很多,例如你无需重写 GetHashCode 和 Equals 之类的方法了。

sealed record ToString 方法

之前 record 的 ToString 是不能修饰为 sealed 的,因此如果你继承了一个 record,相应的 ToString 行为也会被改变,因此这是个虚方法。

但是现在你可以把 record 里的 ToString 方法标记成 sealed,这样你的 ToString 方法就不会被重写了。

struct 无参构造函数

一直以来 struct 不支持无参构造函数,现在支持了:

struct Foo
{
    public int X;
    public Foo() { X = 1; }
}

但是使用的时候就要注意了,因为无参构造函数的存在使得 new struct() 和 default(struct) 的语义不一样了,例如 new Foo().X == default(Foo).X 在上面这个例子中将会得出 false

三、匿名对象的 with

可以用 with 来根据已有的匿名对象创建新的匿名对象了:

var x = new { A = 1, B = 2 };
var y = x with { A = 3 };

这里 y.A 将会是 3 。

四、全局的using

利用全局 using 可以给整个项目启用 usings,不再需要每个文件都写一份。比如你可以创建一个 Import.cs,然后里面写:

global using System;
global using i32 = System.Int32;

然后你整个项目都无需再 using System,并且可以用 i32 了。

五、文件范围的namespace

这个比较简单,以前写 namespace 还得带一层大括号,以后如果一个文件里只有一个 namespace 的话,那直接在最上面这样写就行了:

namespace MyNamespace;

六、常量字符串插值

你可以给 const string 使用字符串插值了,非常方便:

const string x = "hello";
const string y = $"{x}, world!";

七、lambda表达式改进

1. 支持 attributes

lambda 可以带 attribute 了:

f = [Foo] (x) => x; // 给 lambda 设置
f = [return: Foo] (x) => x; // 给 lambda 返回值设置
f = ([Foo] x) => x; // 给 lambda 参数设置

2. 支持指定返回值类型

此前 C# 的 lambda 返回值类型靠推导,C# 10 开始允许在参数列表最前面显示指定 lambda 类型了:

f = int () => 4;

3. 支持 ref 、in 、out 等修饰

f = ref int (ref int x) => ref x; // 返回一个参数的引用

4. 头等函数

函数可以隐式转换到 delegate,于是函数上升至头等函数:

void Foo() { Console.WriteLine("hello"); }
var x = Foo;
x(); // hello

5. 自然委托类型

lambda 现在会自动创建自然委托类型,于是不再需要写出类型了。

var f = () => 1; // Func<int>
var g = string (int x, string y) => $"{y}{x}"; // Func<int, string, string>
var h = "test".GetHashCode; // Func<int>

CallerArgumentExpression

现在,CallerArgumentExpression 这个 attribute 终于有用了。借助这个 attribute,编译器会自动填充调用参数的表达式字符串,例如:

void Foo(int value, [CallerArgumentExpression("value")] string? expression = null)
{
    Console.WriteLine(expression + " = " + value);
}

当你调用 Foo(4 + 5) 时,会输出 4 + 5 = 9。这对测试框架极其有用,因为你可以输出 assert 的原表达式了:

static void Assert(bool value, [CallerArgumentExpression("value")] string? expr = null)
{
    if (!value) throw new AssertFailureException(expr);
}

八、tuple 支持混合定义和使用

int y = 0;
(var x, y, var z) = (1, 2, 3);

于是 y 就变成 2 了,同时还创建了两个变量 x 和 z,分别是 1 和 3 。

九、泛型 attribute

是的你没有看错,C# 的 attributes 支持泛型了,不过 .NET 6 中将以预览特定放出,因此需要 <LangVersion>preview</LangVersion>

class TestAttribute<T> : Attribute
{
    public T Data { get; }
    public TestAttribute(T data) { Data = data; }
}

然后你就能这么用了:

[Test<int>(3)]
[Test<float>(4.5f)]
[Test<string>("hello")]

更多语法变更等待后期探索。....

更多:

.Net 6.0中的新增特性_.Net 6.0中的新增功能

Element-ui和Element-Plus的区别_Element2和Element3的区别

Vue2和Vue3的区别_Vue3和Vue2的区别

Vue3+Element Plus开发搭建_Vue3+Element3开发搭建



这篇关于C# 10新增功能_C# 10新增特性的文章就介绍到这儿,希望我们推荐的文章对大家有所帮助,也希望大家多多支持为之网!


扫一扫关注最新编程教程