【问题标题】:Custom Rules - Disable Constructor Implementation on child Class自定义规则 - 在子类上禁用构造函数实现
【发布时间】:2023-04-09 06:15:02
【问题描述】:

我正在用 C# 编写基于工厂模式的解决方案。

如果有Abstract class 称为AnimalAnimal 的任何子类都将通过工厂模式通过传递类型来实例化。

public abstract class Animal
{
    protected abstract void Constructor();

    public Animal()
    {
        Constructor();
    }
}   

public class Dog : Animal
{
    protected override void Constructor()
    {
        //Constructor Code here
    }
} 

我不会让我的任何队友滥用上面的代码,在他们的子类中声明他们自己的公共构造函数(例如:cat)并直接调用构造函数(例如:Animal cat = new Cat();)而不使用工厂。

如何创建在编译此类时会抛出错误的代码分析规则?

【问题讨论】:

  • 说实话,我不确定为什么你会想要这样做。仅仅使用构造函数会给你带来什么?也许您应该向我们展示工厂的代码?哦,您可能还想了解CA2214when initializers are executed

标签: c# visual-studio oop roslyn roslyn-code-analysis


【解决方案1】:

几个选项:

您可以将类、它的派生类和工厂放入它自己的程序集中,并使类的构造函数内部化。如果 Factory 方法是公共的,那么任何引用程序集的东西都只能通过 Factory 来创建它。

另一种选择是将工厂嵌套在 Animal 类中,例如:

public abstract class Animal
{
    protected abstract void Constructor();

    protected Animal()
    {
        Constructor();
    }

    public class Factory
    {
        public static Animal CreateAnimal()
        {
            return new Animal();
        }
    }
}  

【讨论】:

  • 类本身应该是公共的,只有它们的构造函数应该是内部的。
【解决方案2】:

如果您将任何parameterdummy parameter 添加到base class,则它不会在child classes. 中提供default constructor

例子:

public abstract class Animal
{
    protected abstract void Constructor();

    public Animal(bool DoNotAllowDefaultConstructor)
    {
        Constructor();
    }
}

这样派生类必须使用 base 关键字显式调用基类构造函数

public class Dog : Animal
{
    protected override void Constructor()
    {
        MessageBox.Show("I'm a dog");
    }

    public Dog():base(false)
    {
        MessageBox.Show("I'm a dog's default constructor");
    }
} 

查看here了解更多详细信息

【讨论】:

  • 现在可以直接调用 Animal myAnimal = new Dog(); // 哪个是错的,它跳过了工厂模式
猜你喜欢
  • 1970-01-01
  • 2015-03-15
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-10-26
  • 1970-01-01
  • 2015-11-18
相关资源
最近更新 更多