我有一个DLL,比如A,它实现了解决数学方程式的通用算法。 我有另一个DLL,比如B,它实现了数学方程式 DLL B使用DLL A来解决它的方程,但DLL B必须能够从DLL A执行给定的方程(DLL A实现一些数值,接近方法并“尝试”给定方程的不同值作为其朝向期望数学的步骤解) 现在,DLL A必须“知道”DLL B,反之亦然。
这是一个“糟糕”的设计吗? 我能想到像业余爱好者这样的代码吗? 你会做什么(请记住,DLL A实现了由实现数学方程的不同其他DLL使用的通用算法)?
由于 大卫
答案 0 :(得分:1)
没有理由说DLL A需要明确知道DLL B,它只需要一个接口就能够评估已经给出的方程式来解决。
接口可以由函数签名指定,指向合适函数的指针将由B传递给A,或者它可以表示为抽象类,并且可以传递实际上是派生实例的指针或引用从B到A。
虽然有可能拥有相互依赖的dll,但这通常不是一个好主意。在这种情况下,我认为没有必要。
答案 1 :(得分:1)
似乎A是一个较旧的dll,因为它被许多其他人使用。看起来很糟糕的是你需要更改A以便它明确地调用B,这可能表示你将在A中一次又一次地进行更改。这是坏消息,因为更改A将需要重建所有其他dll。
你需要通过引入你给B的任何形式的回调(虚拟,回调,模板)来抽象B如何执行方程式或A如何求解方程式。我会去B,因为A比较老,可能更常用。这里有一些伪代码,其中Solver是A的一个类,Equation是一类B:
solver=new Solver;
equation=new Equation(&solver);
Solver需要实现某种抽象接口。最佳解决方案取决于您的语言和框架。谷歌的“依赖倒置原则”或“依赖注入”。
答案 2 :(得分:1)
这个问题(包之间实现的循环依赖)正是创建Dependency Inversion Principle (DIP)的原因。 Charles Bailey提供了一个使用DIP来打破依赖性的解决方案。不是将两个具体类直接相互耦合(类或函数,它对应用DIP没有太大区别),而是将它们耦合到抽象中。
在这种情况下,我们有一个定义“数学函数”的接口,它由解算器DLL使用。我们还有一个定义“求解器算法”的接口,它由函数DLL使用。我们有具体的类/函数取决于抽象。在C ++术语中,这些是接口,当在函数DLL中调用方法时,求解器会将自身作为指向“求解器接口”的指针传递给函数。该函数调用求解器接口上的方法以在适当的点回调到求解器。类似地,求解器有一个类,它接受一个指向数学函数接口的指针,并在适当的时候回调函数。
Bob Martin的书Agile Principles, Patterns and Practices in C#涵盖了这些面向对象的设计原则,包括DIP。他有具体的例子,在实践中表明了这些原则。虽然本书使用C#(第一版使用Java),但相同的原则和实践适用于C ++。
答案 3 :(得分:0)
这是一个很好的问题。是的,这将是一个糟糕的设计。两种解决方案:
您可以通过Google搜索“循环”和/或“非循环”依赖关系找到有关此主题的更多信息。
答案 4 :(得分:0)
如果你正在实现一个回调模式,这是一个不错的设计,其中DLL A发布一个回调接口,DLL B根据接口实现回调方法,并在调用A时提供指向它的指针。