我有一个接口和两个实现它的类。我收到编译错误,我不太清楚为什么。
interface IPerson
{
ICollection<string> NickNames{get;set;}
}
class ObservablePerson : IPerson
{
ObservableCollection<string> NickNames{get;set;}
}
class ListPerson : IPerson
{
List<string> NickNames{get;set;}
}
我在理解为什么这不起作用时遇到了一些麻烦,因为List和ObservableCollection都实现了ICollection。
答案 0 :(得分:6)
我在理解为什么这不起作用时遇到了一些麻烦,因为List和ObservableCollection都实现了ICollection。
是的,但界面指出返回ICollection<string>
。基础类型可以是ObservableCollection<string>
或List<string>
,但签名需要符合接口。 ObservableCollection<string>
是ICollection<string>
,但ICollection<string>
不一定是ObservableCollection<string>
。
此外,您的方法需要公开(它们目前是私有的)。接口不处理私有或受保护的方法,它定义了 public 接口。
答案 1 :(得分:1)
应该是
interface IPerson
{
ICollection<string> NickNames{get;set;}
}
class ObservablePerson : IPerson
{
ICollection<string> NickNames{get;set;}
}
class ListPerson : IPerson
{
ICollection<string> NickNames{get;set;}
}
在实现中,您可以返回List对象或ObservableCollection
已编辑的代码
interface IPerson
{
ICollection<string> NickNames{get;set;}
}
public class ObservablePerson : IPerson
{
ICollection<string> nickNames = new ObservableCollection<string>();
public ICollection<string> IPerson.NickNames
{
get
{
return nickNames;
}
set
{
nickNames = value;
}
}
}
public class ListPerson : IPerson
{
ICollection<string> nickNames = new List<string>();
public ICollection<string> IPerson.NickNames
{
get
{
return nickNames;
}
set
{
nickNames = value;
}
}
}
答案 2 :(得分:0)
您的问题是编译器希望您的两个子类都返回一种ICollection类型。您可以通过get访问器返回List或ObservableCollection,但声明的成员类型需要保留ICollection。
答案 3 :(得分:0)
编译器将坚持精确类型匹配,但您可以在类(而不是通过接口)访问时隐藏属性。但请注意,在通过界面进行设置时,某人可能会分配不同类型的ICollection<string>
- 因此这会导致异常。
interface IPerson
{
ICollection<string> NickNames { get; set; }
}
class ObservablePerson : IPerson
{
public new ObservableCollection<string> NickNames { get; set; }
ICollection<string> IPerson.NickNames
{
get { return NickNames; }
set { NickNames = (ObservableCollection<string>)value; }
}
}
class ListPerson : IPerson
{
public new List<string> NickNames { get; set; }
ICollection<string> IPerson.NickNames
{
get { return NickNames; }
set { NickNames = (List<string>)value; }
}
}
答案 4 :(得分:0)
我遇到了类似的问题,我的一个伙伴提出了一个很好的解决方案:通用类型。这是你可以做的:
public interface IPerson<CollectionType> where CollectionType : ICollection<string>
{
CollectionType NickNames { get; set; }
}
class ObservablePerson : IPerson<ObservableCollection<string>>
{
public ObservableCollection<string> NickNames { get; set; }
}
public class ListPerson : IPerson<List<string>>
{
public List<string> NickNames { get; set; }
}
这里,“CollectionType”是一个Generic,并且可以根据需要命名(在整个.NET Framework中它通常称为T,但是给它一个有意义的名称我觉得很有帮助)。这将允许您在那些ObservablePerson和ListPerson上实现一个接口,同时在每个上都有不同类型的NickNames属性(尽管您用于CollectionType的任何类型都需要实现ICollection)。