【问题标题】:Constructor dependency code snippet in visual studioVisual Studio 中的构造函数依赖代码片段
【发布时间】:2021-10-09 02:20:52
【问题描述】:

我发现自己向构造函数添加了很多依赖项:

public class SomeClass() {
    private ISomeService _service;
    private IAnotherService _anotherService;
    public SomeClass(ISomeService service, IAnotherService anotherService) {
        _service = service;
        _anotherService = anotherService;
    }
}

写起来挺乏味的,一直在visual studio中找代码sn-ps自动加一个到构造函数但是没找到。

我想要的是:

  • 向构造函数添加依赖项时,某些 sn-p 会自动创建一个局部变量并分配给它。

  • 添加一个私有变量,然后一些sn-p会自动将其添加到构造函数中,并将其分配给局部变量。

【问题讨论】:

  • 指定目标C#版本以及Visual Studio版本;这可能会提供不同的答案。
  • @OmegaMan vs 2015,.net 4.5
  • 不知道,你在问什么。您想通过选择私有字段来生成构造函数吗?
  • @Jannik 是的,请参阅我的更新答案

标签: c# .net


【解决方案1】:

如果您有R#,您可以输入字段声明,然后突出显示它们并点击Alt-Enter,这将为您提供生成构造函数和字段分配的选项。

【讨论】:

  • 用了几天了,真的很不错。
  • 每隔一段时间,我就会到 stackoverflow 找到一些我会在 vanilla Visual Studio 中使用的“不错的”功能。 90% 的时间,公认的答案是使用 Resharper。我觉得这真的很烦人,因为 Resharper 非常笨重,并且在 IDE 上增加了大量开销......
【解决方案2】:

如果您没有 Resharper,您可以在构造函数中添加参数,将赋值写入不存在的属性并按 CTRL+。 .这将提示您选择自动为您创建属性或字段。

例如,你有这个类:

public class MyClass 
{ 
    public MyClass()
    { 
    }
}

然后您将参数添加到构造函数和赋值:

public class MyClass 
{ 
    public MyClass(IDependency myDependency)
    { 
         this.myDependency = myDependency;
    }
}

然后按 CTRL+。在分配线上,然后选择创建字段,你会得到这个:

public class MyClass 
{         
    IDependency myDependency;

    public MyClass(IDependency myDependency)
    { 
         this.myDependency = myDependency;
    }
}

【讨论】:

  • VS 2017 - 已修复。请参阅下面 Simon Budin 的问题:所有这些现在都是自动化的,工作量比这个答案少得多。
【解决方案3】:

我不知道以前的版本,但是在 vanilla Visual Studio 2017 中,您实际上可以添加构造函数参数

public SomeClass(ISomeService service)
{ 
}

然后将光标放在service 上,然后从“快速操作”中选择Introduce and initialize field _someService,它会做你想做的事:

private readonly ISomeService _someService;

public SomeClass(ISomeService service)
{ 
    _someService = service;
}

【讨论】:

  • 我误读了您的评论,但发生了一个意外:您还可以将光标放在声明上并选择快速操作以将声明的属性/字段添加到构造函数。这为我节省了很多时间,非常感谢。
【解决方案4】:

您可以根据需要轻松添加代码 sn-ps,在 XAML 中定义它并将其添加到编辑器中,您可以使用诸如“类名”之类的占位符将其用作构造函数,然后将变量放入它作为静态文本

我不想写代码,因为它是重复的 你可以在这里查看如何操作: https://msdn.microsoft.com/en-us/library/ms242312.aspx?f=255&MSPPError=-2147217396

你也可以看到这个问题: How can I automatically generate a constructor that receives and stores services for free?

【讨论】:

    【解决方案5】:

    你试图用 ISomeService 和 IAnotherService 做的是依赖倒置。

    我强烈建议您将它与依赖注入框架结合使用。有很多可用的,但我推荐的一个是 MEF。 MEF 内置于 .net 框架中。例如,使用 MEF 时,您的代码将如下所示

    [Export(typeof(ISomeService))]
    public class SomeService : ISomeService {
    }
    
    
    public class SomeClass {
    
       [Import]
       public ISomeService SomeService {get; set;}
    
       [Import]
       public IAnotherService AnotherService {get; set;}
    
    }
    

    现在,MEF 实际上会确保在创建类时填充您的 SomeService 和 AnotherService 属性。它将构造(如果需要)SomeService 的实例,填充它的所有依赖项并将其放入正确的属性中。您甚至可以控制是否希望您的服务在每次需要时实例化为单例或作为新的服务实例。

    有关 MEF 的更多详细信息,您可以查看此处https://msdn.microsoft.com/en-us/library/ee155691(v=vs.110).aspx

    这应该避免编写许多除了初始化服务之外什么都不做的构造函数。

    【讨论】:

    • 我正在使用 simpleinjector。我不是在问如何做di。似乎您所做的只是属性注入,我想避免这种情况,因为它鼓励像上帝一样的课程。
    • 你对如何避免编写乏味的样板文件很感兴趣。如果我有 IGodService 属性,或者如果我将 IGodService 作为参数添加到构造函数。任何一种都允许开发人员编写糟糕的代码。这种方式(propertyInjection)只是避免了样板
    • 您对繁琐的样板化是正确的,感谢您的建议。我的意思是类本身(一个正在注入的地方)更有可能成为具有属性注入的神类,因为您看不清楚您实际注入了多少依赖项。并不是说它本身是错误的(这是一个全新的讨论),当然是一个相关的答案,只是不是我想要的。
    【解决方案6】:

    Telerik 的 JustCode 可以完全满足您的需求。
    如果您在构造函数中有一个未使用的参数,您可以创建一个字段并对其进行初始化。 http://www.telerik.com/products/justcode/quick-fixes.aspx

    【讨论】:

      【解决方案7】:

      当我发现这个library 的 sn-ps 时,我正在寻找这个。根据您需要多少参数,您可以使用 ctor1p、ctor2p.. 等等。它创建指定参数数量的构造函数,并生成对应于每个注入参数的私有字段。

      当你第一次编写构造函数时它工作得很好。

      如果你有一个现有的带/不带参数的构造函数,并且你想使用这些 sn-ps 注入一个新参数,你将不得不重写你的构造函数,这比手动注入参数和使用 ctrl + 更困难..

      【讨论】:

        猜你喜欢
        • 2011-04-21
        • 2020-09-07
        • 1970-01-01
        • 2016-11-17
        • 2011-07-05
        • 1970-01-01
        • 2019-03-24
        • 1970-01-01
        相关资源
        最近更新 更多