6

我有一个非常简单的场景:“”可以是公司的“客户”或“员工”。

可以使用“呼叫”方法通过电话呼叫“人”。

根据“”在通话中扮演的角色,例如新产品的发布或组织变更的声明,我们应该使用为“客户”角色提供的电话号码或提供的电话号码对于“员工”角色。

以下是情况的总结:

interface IPerson
{
    void Call();
}

interface ICustomer : IPerson
{
}

interface IEmployee : IPerson
{
}

class Both : ICustomer, IEmployee
{
    void ICustomer.Call()
    {
        // Call to external phone number
    }

    void IEmployee.Call()
    {
        // Call to internal phone number
    }
}

但是此代码无法编译并产生错误:

error CS0539: 'ICustomer.Call' in explicit interface declaration is not a member of interface
error CS0539: 'IEmployee.Call' in explicit interface declaration is not a member of interface
error CS0535: 'Both' does not implement interface member 'IPerson.Call()'

这种情况是否有机会以不同的方式在 C# 中实现,还是我必须找到另一种设计?

如果是这样,您提出了哪些替代方案?

在此先感谢您的帮助。

4

6 回答 6

9

你的目标没有意义。

既不ICustomer也不IEmployee定义Call()方法;他们只是从同一个接口继承方法。您的Both类两次实现相同的接口。
任何可能的Call调用都会调用IPerson.Call;没有 IL 指令会专门调用ICustomer.Callor IEmployee.Call

您可以通过Call在两个子接口中显式重新定义来解决此问题,但我强烈建议您只给它们不同的名称。

于 2010-12-07T17:51:11.943 回答
2

我对您对我的解决方案的意见感兴趣...

当我希望控制器访问我的类上的一些属性或方法时,我经常使用组合的显式实现,而这些属性或方法应该在类的常规使用中隐藏......

因此,为了能够有多个 IPerson 实现,在这个例子中,我将使用泛型,以便能够将 IPerson 接口从客户拆分为员工

interface IPerson<T>
{
    void Call();
}

interface ICustomer : IPerson<ICustomer>
{
}

interface IEmployee : IPerson<IEmployee>
{
}

class Both : ICustomer, IEmployee
{
    void IPerson<ICustomer>.Call()
    {
        // Call to external phone number 
    }

    void IPerson<IEmployee>.Call()
    {
        // Call to internal phone number 
    }
} 
于 2012-06-21T18:29:15.907 回答
1

我自己遇到了这个。

您可以通过使用组合来解决问题:

interface IPerson
{
    void Call();
}

interface ICustomer : IPerson
{
}

interface IEmployee : IPerson
{
}

class Both
{
    public ICustomer Customer { get; }
    public IEmployee Employee { get; }
}

以上假设 Both 类中的 Employee 是 IEmployee 的自定义实现,并且是基于 Both 对象构造的。

但这取决于您计划如何使用 Both 类。
如果你想像这样使用 Both 类:

((IEmployee)both).Call();

然后你可以使用这个:

both.Employee.Call();
于 2012-05-08T21:19:22.550 回答
1

除了 SLaks 准确指出的问题...

去掉IPersoncreateIContactable的一个方法Contact(),然后 Create 两个具体的类型调用CustomerEmployee实现IContactable。然后,每当您需要联系某人时,您可以IContactable.Contact()根据需要调用您的方法,因为能够进行联系可以扩展,而IPerson有点抽象。

于 2010-12-07T17:59:15.710 回答
0

我不知道这是否有帮助,但你可以试一试。

//ran in linqpad c# program mode, you'll need to provide an entry point.....
void Main()
{
    IPerson x;
    x = new Both(new Employee());
    x.call(); //outputs "Emplyee"
    x = new Both(new Customer());
    x.call(); //outputs "Customer"
}

class Customer :  ICustomer
{
    public void call() {"Customer".Dump();}
}
class Employee :  IEmployee
{
    public void call() {"Employee".Dump();}
}
class Both : IPerson
{
     private IPerson Person { get; set; }
     public Both(IPerson person)
     {
         this.Person = person;
     }
     public void call()
     {
        Person.call();
     }
} 
interface IPerson { void call(); }  
interface ICustomer : IPerson { } 
interface IEmployee : IPerson { } 
于 2010-12-07T18:31:18.057 回答
0

您不能这样做,因为在这两种情况下 Call 方法来自 IPerson 接口。因此,您尝试定义 Call 方法两次。我建议您将 ICustomer 和 IEmployee 接口更改为类,并在此类中定义 Call 方法:

interface IPerson
{
    void Call();
}

class Customer : IPerson
{
    public void Call()
    {
    }
}

class Employee : IPerson
{
    public void Call()
    {
    }
}
于 2010-12-07T17:59:42.450 回答