Dependency injection 依赖注入问题(双向通信)

Dependency injection 依赖注入问题(双向通信),dependency-injection,Dependency Injection,我有a一个a的实例和b一个b a必须能够调用b上的方法,并且b如果某些检查通过,则必须立即调用a上的方法 要实现这一点,我需要循环DI public A(B b) { _b = b; } public void CallToB() { _b.Method(); } public void Method() { DoSomething(); } public B(A a) { _a = a; } public void Method() { if (SomeCheck()) _a.Method(

我有
a
一个
a
的实例和
b
一个
b

a
必须能够调用
b
上的方法,并且
b
如果某些检查通过,则必须立即调用
a
上的方法

要实现这一点,我需要循环DI

public A(B b) { _b = b; }
public void CallToB() { _b.Method(); }
public void Method() { DoSomething(); }

public B(A a) { _a = a; }
public void Method() { if (SomeCheck()) _a.Method(); }
我知道我可以利用事件来绕过它,让
b
不知道/不依赖
a
。但这感觉是不对的


注意:在双向通信成为可能的情况下,我还没有看到这个问题的答案。

您可以通过依赖接口而不是具体类型来解决这个问题,然后使用属性注入。以下是一个例子:

public interface IA
{
    void Method();
}

public class A : IA
{
    private readonly IB _b;
    public A(IB b){_b = b;}
    //...
}

public interface IB
{
    void Method();
}

public class B : IB
{
    private readonly IA _a;
    public B(IA a){_a = a;}
    //...
}

public class BCycleDependencyBreaker : IB
{
    private IB _b;

    public IB b
    {
        set { _b = value; }
    }

    public void Method()
    {
        _b.Method();
    }
}
然后,当您这样编写时,使用
BCycleDependencyBreaker

var b_cycle_dependency_breaker = new BCycleDependencyBreaker();

//Make a depend on this implementation of b that currently does nothing
A a = new A(b_cycle_dependency_breaker); 

//Make b depend on a
B b = new B(a);

//Now, let the proxy implementation delegate calls to the real b
b_cycle_dependency_breaker.b = b;

这就是为什么最好避免循环依赖。。(如果使用接口,则在实现本身之间没有建立循环-如果通过IoC或其他注入完成,则在循环的“外部”连接)循环依赖通常表示设计缺陷-如果您可以控制这些类,我建议将
A
B
中的任何常见依赖项提取到第三个类中,以便
A
B
都依赖于该类,而不是彼此依赖。