处理从接口继承的对象之间的差异

本文关键字:之间 对象 处理 接口 继承 | 更新日期: 2023-09-27 17:50:28

我有两个对象继承了我创建的一个接口,它工作得很好。对象被注入到另一个对象中,调用两个对象的方法。对象的方法执行一些简单的XML操作,然后返回给工作对象。

我现在有一个更改请求,它影响了从接口继承的一个对象,但不影响另一个对象,我不知道该如何处理这个问题。我创建了几个新方法,如果它没有使用,我只是抛出一个未实现的异常。这似乎不是"最佳实践"。给我。处理这种情况的最佳方法是什么?

处理从接口继承的对象之间的差异

我认为这是接口隔离原则发挥作用的情况。

如果您发现两个对象公开相同的公共成员集没有意义,那么它们可能不应该实现相同的接口。或者至少不只是相同的接口。根据应用程序的逻辑,这里有两个选项:

  1. 保持原来的接口不变,不修改第一个类(不需要额外方法的类)。

  2. 仅为新方法定义一个新接口,并使第二个类实现两个接口。
  3. 定义一个继承旧接口并包含新方法的新接口。保持第一个类不变,让第二个类实现新的接口。

实现一个接口,但在某些方法中除了抛出异常之外什么都不做,这确实是一种不好的做法,因为它违反了Liskov替代原则。

接口不需要完全实现…即使在。net中,也有部分实现接口的类(并且当以"非法"方式使用时抛出NotSupportedException())……例如数组是IList<>,不支持Add()Remove()

或者Stream抽象类,它有一个额外的"模式":CanRead, CanWrite, CanSeek,…,因此有一些方法和属性来判断使用这些方法是否合法。

另一种方法是使用额外的接口,并尝试使用as操作符强制转换它。实体框架例如"返回"IQueryable<T>,那"是"IEnumerable<T>…但是这些对象甚至支持IDbAsyncEnumerable<T>接口……但并非所有的IQueryable<T>都是IDbAsyncEnumerable<T>。你必须进行强制转换,看看接口是否存在。

您可以这样扩展接口:

public interface SimpleInterface 
{
    void SimpleMethod();
    void OtherMethod();
}
public interface ExpandedInterface : SimpleInterface
{
    void ExpandedMethod();
    void OtherExpandedMethod();
}

这样你就可以在你的客户端代码中声明,如果你真的需要一个扩展的接口实现者(在这种情况下,你应该只传递实现ExpandedInterface的具体类子集的一个实例)或者使用SimpleInterface实现者(在这种情况下,你可以传递任何一个)。

您所呈现的情况(需要向一个对象添加函数,但不需要向另一个对象添加函数)与客户端代码的关系比与接口实现本身的关系更大。您必须思考:"在这个客户端类中,我真正需要的是什么:SimpleInterface的实例,还是ExtendedInterface的实例?"