[英]Explicit interface implementation limitation
我有一個非常簡單的場景:“ 人 ”可以是公司的“ 客戶 ”或“ 員工 ”。
一個“ 人 ”,可以通過電話與“ 呼叫 ”的方法被調用。
根據“ 人 ”在通話環境中扮演的角色,例如新產品的公告或組織變更的公告,我們應該使用為“ 客戶 ”角色提供的電話號碼或提供的電話號碼為“ 員工 ”角色。
以下是對情況的總結:
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#中實現,還是我必須找到另一種設計?
如果是這樣,你建議用什么替代品?
在此先感謝您的幫助。
你的目標沒有意義。
ICustomer
和IEmployee
都沒有定義Call()
方法; 他們只是從同一個接口繼承該方法。 您的Both
類兩次實現相同的接口。
任何可能的Call
呼叫將始終呼叫IPerson.Call
; 沒有專門調用ICustomer.Call
或IEmployee.Call
IL指令。
您可以通過在兩個子接口中顯式重新定義Call
來解決此問題,但我強烈建議您只是給它們不同的名稱。
我自己也碰到了這個。
您可以使用組合來解決問題:
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();
我對我的解決方案的輸入感興趣...
當我希望控制器訪問我的類中的一些屬性或方法時,我使用了很多組合的顯式實現,這些屬性或方法應該隱藏在類的常規用法中...
因此,為了能夠多次實現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
}
}
除了SLaks准確指出的問題......
擺脫IPerson
並使用Contact()
方法創建IContactable
,然后創建兩個實現IContactable
稱為Customer
和Employee
具體類型。 然后,當你需要聯系某人時,你可以根據需要調用你的IContactable.Contact()
方法,因為能夠進行聯系可以擴展,而IPerson
有點抽象。
你不能這樣做,因為Call方法來自兩種情況下的IPerson接口。 因此,您嘗試兩次定義Call方法。 我建議您將ICustomer和IEmployee接口更改為類,並在此類中定義Call方法:
interface IPerson
{
void Call();
}
class Customer : IPerson
{
public void Call()
{
}
}
class Employee : IPerson
{
public void Call()
{
}
}
我不知道這是否有幫助,但你可以試一試。
//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 { }
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.