在我的日常编程中,我尽量遵循solid原则和其他设计模式,但在某些情况下会变得困难,特别是使用依赖反转原则,对于层次类来说,创建一个工厂类并将对象存储在那里可能很容易,对于单例或构建器也是如此,但是当你在方法中使用单个类对象时,问题就会出现,它是不断变化的,同样没有层次关系
//在这里,在newTaskFor()方法中,dip原则被违反了,那么如何在daily程序或它的容器类中使用新关键字可以解决这样的问题
protected <T> RunnableFuture<T> newTaskFor(Callable<T> callable) {
return new FutureTask<T>(callable); //violating Dip principle
}
/**
* @throws RejectedExecutionException {@inheritDoc}
* @throws NullPointerException {@inheritDoc}
*/
public Future<?> submit(Runnable task) {
if (task == null) throw new NullPointerException();
RunnableFuture<Void> ftask = newTaskFor(task, null);
execute(ftask);
return ftask;
}发布于 2021-05-18 09:16:37
在某处总会有一些凝固物。如果你想对所有东西都应用DIP,那么几乎所有的类型都必须被隐藏在高级的特定接口后面,一遍又一遍,这是不实用的。
例如,声明newTaskFor的高级模块可以很好地构建自己的Future抽象,这些抽象不会直接耦合到Java,但这可能会有很大的工作量,而带来的好处很少?
我经常问自己这个问题的一个很好的例子是,当我设计了一个简单的网络爬行库,它必须处理相当多的HTML文档。我可以选择是耦合到特定的库(如Jsoup ),还是创建自己的抽象以避免紧密耦合。因为我最终必须支持复杂的文档查询和操作,所以我发现在Jsoup之上创建另一个抽象层是非常不切实际的,因为我必须重新定义几乎所有的节点接口。
然而,在这些情况下有效抽象的关键是只关注系统真正需要的API部分,剩下的部分留下来,并确保以特定于领域的方式表达抽象。如果你最终模仿了整个API,那么你的抽象很可能会受到特定实现的高度影响。如果您发现您需要底层库的所有功能,那么将其抽象出来可能代价太高。
编辑:
我刚刚检查了一下,似乎我在第三段中撒谎了,我最终像下面这样制作了一个API (几年前,我似乎只支持我拥有的最小用例,而不是一个复杂的库),但甜蜜的是,Scraper只支持非常基本的提取,抽象可能最终弊大于利。

https://stackoverflow.com/questions/67194761
复制相似问题