在C#中,不允许实现这样的接口:
public interface ITest
{
IEnumerable<int> Numbers { get; set; }
}
public class CTest : ITest
{
public List<int> Numbers { get; set; }
}
Run Code Online (Sandbox Code Playgroud)
我的问题是:是否有一些软件哲学使这种类型的实现错误?它是一种有争议的范式,有点像多重继承,其中争论已经发生了几十年?
我看不出为什么这样的接口实现不能正常工作的任何原因.如果你知道ITest,那么你只能看到它的IEnumerable<int>一部分CTest.Numbers.如果您了解CTest,那么您可以使用整个List<int>实现.既然List<int>源自IEnumerable<int>,为什么它不满足接口要求?
在重写基本方法时子类返回子类型的能力称为返回类型协方差
在这种情况下,由于Numbers属性的setter,您的示例是不安全的:
ITest t = new CTest();
t.Numbers = new HashSet<int>();
Run Code Online (Sandbox Code Playgroud)
如果只有一个getter定义,ITest那么它将是安全的,虽然C#仍然不允许它 - 但Java确实如此:
public interface Test {
Iterable<Integer> getNumbers();
}
public class CTest implements Test {
public List<Integer> getNumbers() {
List<Integer> numbers = new ArrayList<>();
numbers.add(1);
return numbers;
}
}
Run Code Online (Sandbox Code Playgroud)