3

我有两个这样的接口:

public interface IMyInterface1
{
    string prop1 { get; set; }
    string prop2 { get; set; }
}

public interface IMyInterface2
{
    string prop1 { get; set; }
    IList<IMyInterface1> prop2 { get; set; }
}

我定义了两个实现接口的类:

public class MyClass1 : IMyInterface1
{
     public string prop1 {get; set;}
     public string prop2 {get; set;}
}

public class MyClass2 : IMyInterface2
{
     public string prop1 {get; set;}
     public IList<MyClass1> prop2 {get; set;}
}

但是当我构建代码时,我收到以下错误消息:

“ClassLibrary1.MyClass2”没有实现接口成员“ClassLibrary1.IMyInterface2.prop2”。“ClassLibrary1.MyClass2.prop2”无法实现“ClassLibrary1.IMyInterface2.prop2”,因为它没有匹配的返回类型“System.Collections.Generic.IList”

如何在我的班级上实现 IMyInterface2 的“IList prop2”?

4

5 回答 5

8

您的接口要求实现类提供类型的属性,而IList<IMyInterface1>不是IList<class that implements IMyInterface1>

IMyInterface2如果你想让它工作,你需要通用:

public interface IMyInterface2<T> where T : IMyInterface1
{
    string prop1 { get; set; }
    IList<T> prop2 { get; set; }
}

然后MyClass2变成:

public class MyClass2 : IMyInterface2<MyClass1>
{
     public string prop1 {get; set;}
     public IList<MyClass1> prop2 {get; set;}
}
于 2010-09-09T13:02:54.343 回答
1

这是因为您的接口MyInterface2有一个属性,它是类型的通用列表,IInterface1并且在实现此接口的类中,即MyClass2您已将该属性声明为类型列表MyClass1

要解决此问题,请将 的类定义更改Prop2为 的列表MyInterface1或将 的接口定义更改Prop2为 的列表MyClass1

例如

public interface MyInterface2
{
    public IList<MyInterface1> Prop2 { get; set; }
}

public class MyClass2 : MyInterface2
{
    public IList<MyInterface1> Prop2 { get; set; }
}
于 2010-09-09T13:01:32.733 回答
1

我不确定我是否会将其称为昨天问题的重复,但是...

.NET 不支持返回类型协方差。这意味着您不能从实现需要更通用类型的接口的类返回派生类型。

解决方法是显式实现给您带来麻烦的接口成员:

public class MyClass2 : IMyInterface2
{
    public string prop1 { get; set; }
    public IList<MyClass1> prop2 { get; set; }
    public IList<IMyInterface1> IMyInterface2.prop2
    {
        get { return prop2.Cast<IMyInterface1>.ToList(); }
        set { prop2 = value.Cast<MyClass1>().ToList(); }
    }
}

但是,在这种情况下,如果您尝试调用,那么显式实现这样的接口将导致问题,IMyInterface.prop2.Add()因为IMyInterface.prop2不再引用与 prop2 相同的集合。

解决问题的另一种方法是实现 Adam 的建议并进行IMyInterface2泛型,以便您可以提供任何实现IMyInterface1.

于 2010-09-09T13:02:24.447 回答
0

MyClass2必须实现接口中声明的属性:

public class MyClass2 : IMyInterface2
{
     public string prop1 {get; set;}
     public IList<IMyInterface1> prop2 {get; set;}
}

即使MyClass1implements IMyInterface1,它也可能在以下情况下引起问题:

IMyInterface2 myInterface2 = new MyClass2();
myInterface2.prop2.Add(new OtherImplementationOfIMyInterface1());

任何使用该类的人都希望能够分配任何实现的实例,IMyInterface1但该类期望MyClass1.

于 2010-09-09T13:00:18.273 回答
0

尝试实现这样的代码的问题是这样的。如果编译器允许您编译该代码,那么您可以编写如下代码:

public class MyClass3 : IMyInterface1 
{ 
    public string prop1 {get; set;} 
    public string prop2 {get; set;} 
} 

...

MyClass2 mc2 = new MyClass2();
IMyInterface2 mi2 = mc2;
mi2.prop2 = new List<MyClass3>();

该接口应该允许您将任何 IList<IMyInterface2> 放入 prop2,但 MyClass2 无法处理。这就是为什么您不能按照您的建议实现可写属性。

于 2010-09-09T13:07:52.387 回答