前往小程序,Get更优阅读体验!
立即前往
发布
社区首页 >专栏 >C# 13 Preview 的 field keyword

C# 13 Preview 的 field keyword

作者头像
郑子铭
发布2024-11-23 13:13:01
发布2024-11-23 13:13:01
7100
代码可运行
举报
运行总次数:0
代码可运行

C# 13 Preview 的 field keyword

Intro

C# 13 将以预览版的特性推出 field keyword 特性,等了几年的功能终于要能用上了,目前在最新版本的 VS 预览版本(17.12.0 Preview 3)中已经可用,不过可惜的是 .NET 9 RC 2 SDK 还不支持,得等到 .NET 9 正式版本了

Sample

field keyword 特性是指在属性(Property)的上下文中支持使用 field 关键词来引用属性背后的字段

我们来看下自动属性的示例:

代码语言:javascript
代码运行次数:0
复制
public string Name { get; set; }

这等同于

代码语言:javascript
代码运行次数:0
复制
private string _name;
public string Name
{
    get => _name;
    set => _name = value;
}

使用 field 关键词改一下如下:

代码语言:javascript
代码运行次数:0
复制
public string Name
{
    get => field;
    set => field = value;
}

再来看一个实际一点使用示例:

代码语言:javascript
代码运行次数:0
复制
internal static class FieldKeywordSample
{
    public static string Name
    {
        get;
        set => field = value?.Trim() ?? string.Empty;
    } = string.Empty;
}

这个示例我们每次对 setter 做了一个 Trim() 的操作,并且保证不给 field 设置 null, null 时设置为 string.Empty

这在之前版本我们就得先声明成下面这样:

代码语言:javascript
代码运行次数:0
复制
internal static class FieldKeywordSample
{
    private static string _name;
    public static string Name
    {
        get => _name;
        set => _name = value?.Trim() ?? string.Empty;
    } = string.Empty;
}

需要声明这个字段并且 getter 也需要写完整,即使没有特殊逻辑直接返回了字段

使用 field 关键词之后就无需声明字段了,并且如果是直接返回或者设置 value 就可以使用自动属性的写法,如下:

代码语言:javascript
代码运行次数:0
复制
public int Num { get => field > 0 ? field : 0; set; }
public int Num2 { get; set => field = value > 0 ? value : 0; }

所以之前这个功能也被称为半自动属性,public string Name { get; set; } 则是完全自动属性

除了这样 getter/setter 直接使用,我们也可以在 getter 返回之前、setter set 之前以及之后做一些自定义的操作,如下:

代码语言:javascript
代码运行次数:0
复制
internal static class FieldKeywordSample
{
    public static string Name
    {
        get;
        set => field = value?.Trim() ?? string.Empty;
        //set;
    } = string.Empty;

    public static string Description
    {
        get => field ?? string.Empty;
        set
        {
            Console.Write(">>>");
            Console.WriteLine(field);
            Console.WriteLine($"Before set description, {nameof(value)}: {value}");
            field = value?.Trim()!;
            // CS0103: The name 'field' does not exist in the current context
            // Console.WriteLine($"After set description, {field}");
            Console.WriteLine("After set description");
            Console.Write(">>>");
            Console.WriteLine(field);
        }
    } = default!;

    public static void Run()
    {
        Name = " Hello ";
        Console.WriteLine(Name);
        Console.WriteLine(Name.Length);

        Console.WriteLine(Description is not null);
        Description = " World ";
        Console.WriteLine(Description);
        Console.WriteLine(Description.Length);
    }
}

输出结果如下:

output

反编译

More

需要注意,想要体验这个特性的话需要将 LangVersion 设置为 preview 才可以。

注意前面的代码的话会看到注释里有一个 error,当在插值字符串中使用 field 关键词的时候会报错

已经有 PR 在修这个问题了 https://github.com/dotnet/roslyn/pull/75566

dotnet-exec 的预览版本中也支持了这一特性,从这个特性合并到 main 分支开始就在等待发布新的 Roslyn nuget 包

但是一直没有更新,所以后面使用了 Roslyn 的 daily build 版本,额外添加了一个 nuget source https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json,感兴趣的话可以看看 nuget.config https://github.com/WeihanLi/dotnet-exec/blob/main/nuget.config

使用下面这个命令来安装 dotnet-exec tool 来体验,因为还是预览版特性,需要使用 --preview option 来使用这个特性

代码语言:javascript
代码运行次数:0
复制
dotnet tool update -g dotnet-execute --prerelease

References

  • https://github.com/dotnet/csharplang/blob/main/proposals/field-keyword.md
  • https://github.com/dotnet/csharplang/issues/140
  • https://github.com/dotnet/roslyn/pull/75566
  • https://github.com/WeihanLi/SamplesInPractice/blob/main/net9sample/CSharp13Samples/FieldKeywordSample.cs
  • https://github.com/WeihanLi/dotnet-exec/blob/main/nuget.config
本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2024-11-15,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 DotNet NB 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • C# 13 Preview 的 field keyword
    • Sample
    • More
    • References
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档