是圆形类依赖从一个编码风格点不好?(Are circular class dependencies

2019-06-21 07:06发布

是圆形类依赖从一个编码风格点不好?

例:

在数据库应用程序,我们有两个班,约一个单一的数据库(一个封装信息DBInfo )和一个类可以创建一个数据库连接。 ( ConnFactory

DBInfo拥有getConnection其使用方法ConnFactory创建连接。 但ConnFactory本身需要一个DBInfo对象这样做。

像这样的:(忽略了可读性的原因任何编码风格)

class DBInfo {
    String name;
    String connectionUrl;

    Connection getConnection() {
        return ConnFactory.getConnection(this);
    } 
}


class ConnFactory {
    Connection getConnection(DBInfo toWhat) {
        return new Connection(toWhat.connectionUrl);
    }
}

我的同事认为,这是不好的做法,如果有没有圆形的像这里的依赖只有一个方向是可能会更好。

这是不好的做法,反模式或代码味道? 有什么缺点?

Answer 1:

在一般情况下,我会叫循环依赖一个代码味道。 注意,术语“代码味道”主要指“这里是一段代码,需要特别注意,并有可能从重新设计中获益。”

在大多数情况下,我会认真考虑一个设计,其中一个循环依赖是没有必要的,但在少数情况下,可能会好起来。

在您的例子中,ConnFactory似乎是多余的,但可能是因为你的榜样已经下调。 在我看来,不过,连接创建逻辑会更好,如果它被转移到了DBINFO类。 当你已经有一个包含有关数据库数据的类,它似乎只是自然让它负责创建该数据库的连接。



Answer 2:

是的,一般来说循环依赖是不好的,但并不总是坏事。 与循环依赖的问题包括紧密耦合,相互依存的模块和一般多米诺效应,当一个模块中的变化传播到其他模块。

在这就是说,你的代码违反单一职责原则DBInfo不但存储有关数据库的信息,而且还负责获取Connection对象。 删除的功能,特别是一块独立的阶级,一切都会好起来。



Answer 3:

不必要

我不认为在粒度级别的循环依赖是不好的。 我没有看到一个问题,如果两个,三个或者是四个类是相互依存的。 (我不是说这是你想要的东西,但它可以在某些情况下确定)。

一个问题,如果你有在封装或模块级的相互依存,上面和下面提及的所有原因。



Answer 4:

此代码仅适用ConnFactory.getConnection()是静态的。 更好的解决方案是使getConnection()的实例方法ConnFactory 。 然后你DBINFO可以采取ConnFactory作为参数(可能是在构造函数中,如果你有一个重载的构造函数)。 但是,我认为这种情况下,可以使用静态方法的更多的是一种不好的做法比圆形参考。

如果你走这条路线,不过,我也将成为一个接口IConnFactoryDBInfo将与和互动ConnFactory将实施。 则没有循环引用-既DBInfoConnFactory将取决于IConnFactory ,这将取决于两者都不是。



Answer 5:

我所知道的是,循环依赖会变得有点问题,当你开始使用依赖注入框架如构造图。 大多数这些框架有麻烦处理循环依赖,有时会导致堆栈溢出异常(原谅双关语:-))。因此我倾向于尽量避开它,除非绝对必要的,无法避免。



Answer 6:

怎么样的双向一个一对多关系,即是在使用ORM层的任何应用这种常见的情况? 这难道不是一个循环依赖的情况?

它是坏/代码味道?



Answer 7:

循环依赖是不好的,因为:

  • 两个依赖超过一个
  • 你无法增量测试(不嘲笑他们中的一个,这将是傻小,紧密耦合的东西)。

你可以做所有的东西与接口如果需要打破循环依赖,但简单的最小的解决方案是只是让DBINFO嵌套类ConnFactory的。 引用本身的单位不是圆形的。



文章来源: Are circular class dependencies bad from a coding style point of view?