代码之家  ›  专栏  ›  技术社区  ›  Nikolaj Dam Larsen

我可以用C#9记录作为选项吗?

  •  3
  • Nikolaj Dam Larsen  · 技术社区  · 5 年前

    我刚刚开始玩C#9和.NET5.0,特别是新的 record 构造。我发现对于记录类型的速记语法我有很多优秀的用例。

    我考虑过的一个用例是使用 记录 让dto进入 IOptions<> ,而不是常规类ASP.NET核心应用程序。这些选项类通常都很简单,所以我认为这是一个完美的匹配,但似乎我不能让它很容易地工作,因为配置应用程序使用 IOPS<> 要求对象具有无参数构造函数。

    public record MyOptions(string OptionA, int OptionB);
    
    public class Startup
    {
        public void ConfigureServices(IServiceCollection services) {
            services.Configure<MyOptions>(Configuration.GetSection(nameof(MyOptions)));
        }
    ...
    }
    
    public class MyController : Controller 
    {
        private readonly MyOptions _options;
        public MyController(IOptions<MyOptions> options) {
            _options = options.Value;  // This throws an exception at runtime
        }
    }
    
    

    上面的示例在尝试访问 IOption<>.Value 属性:

    有没有办法配置 IOptions 配置系统使用记录的构造函数反序列化选项,而不需要无参数构造函数?

    我可以对记录使用longhand语法,但是使用类没有什么好处。

    1 回复  |  直到 5 年前
        1
  •  8
  •   Blindy    5 年前

    有没有办法配置IOptions配置系统,使用记录的构造函数反序列化选项,而不需要无参数构造函数?

    不,一般来说ASP.NetCore使用了大量的运行时类型实例,这需要预先知道的构造函数调用,在这种情况下,它需要一个没有参数的构造函数。

    但是,可以使记录类具有无参数构造函数:

    public record MyOptions(string OptionA, int OptionB)
    {
        public MyOptions(): this(default, default) {}
    }
    

    值得吗?嗯。由你决定。它并不比普通的课程差,从性能上看,所以你可以选择任何你觉得更清楚的课程!

    编辑:或者,您应该能够使用此表单:

    public record MyOptions(string OptionA = default, int OptionB = default);