现在,我有一种困境。有一个类似于以下结构的类结构:

public interface IMammal
{
    void Eat();
}

public interface IBarking
{
    void Bark();
}


IBarkingIMammal的实例。从理论上讲,我们的动物可以是其中之一,也可以只是其中之一。如您所见,CowIMammalDogIMammalIBarking。从理论上讲,我们甚至可以有一个可以吠叫但不是哺乳动物的人。

public class Mammal : IMammal
{
    public void Eat()
    {
        Console.Write("Om-nom-nom");
    }
}

public class Cow : Mammal
{
}

public class Dog : Mammal, IBarking
{
    public void Bark()
    {
        Console.Write("Bark-bark!!!");
    }
}


这是一个Farm,其中只有一只动物生活:

public class Farm
{
    private readonly IMammal _animal;

    public Farm(IMammal animal)
    {
        _animal = animal;
    }

    public void Feed()
    {
        _animal.Eat();
    }

    public void Guard()
    {
        var dog = _animal as IBarking;
        if (dog != null)
            dog.Bark();
    }
}


我在这里可以看到的问题是,我们假定IBarking始终为IMammal。这种设计有什么问题,如何解决?

最佳答案

这样简化的例子几乎没有任何意义。您缺少“问题案例”以及接下来要做什么。显示实现IBarking但不实现IMammal的类,以及将其传递给Farm时会出现什么问题。无论如何,鉴于前提:


接口IMammal存在。
接口IBarking存在。
实现IBarking的类不必实现IMammal
类构造函数Farm必须接受IBarkingIMammal
当前的类构造函数接受IMammal


在这种情况下,您将需要一个新的构造函数,一个新的私有成员以及在这两者之间进行选择的更多代码,或者一个重叠的接口。我会选择后者:IFarmable

然后,您需要:


public interface IMammal : IFarmable
public interface IBarking : IFarmable
public Farm(IFarmable farmable) { ... }


您很可能还有其他约束,例如“但我想在传递给构造函数的变量上调用Eat()”,但随后您的描述(“我们假定IBarking始终为IMammal”)不正确或不完整,并且您需要将Eat()移至IFarmable界面。

10-06 12:35