已关闭。这个问题是opinion-based。它目前不接受答案。
**想要改进这个问题吗?**更新问题,以便editing this post可以用事实和引用来回答它。
昨天关门了。
社区正在评估是否在18小时前重新讨论这个问题。
Improve this question
假设您正在为某个集合编写一个算法,例如,为某个List
编写一个方法‘CONTAINS’。代码可能如下所示(出于示例的目的,这非常简单):
def betterContains(list: List[String], element: String): Boolean = {
if (list.isEmpty) false
else if (list.head == element) true
else betterContains(list.tail, element)
}
想象一个更复杂的算法,例如在树、图等中搜索元素。出于某种原因,您添加了用于日志记录的代码:
def betterContains(list: List[String], element: String): Boolean = {
if (list.isEmpty) {
log.info("The element was not found in the list.")
false
}
else if (list.head == element) {
log.info("Yes! found it!")
true
}
else {
log.info(s"Still searching, ${list.tail.size} elements pending")
betterContains(list.tail, element)
}
}
然后,假设您正在添加用于将一些进度数据保存在文本文件中的代码。最后,您将拥有一个做3件事的方法:
- 在列表中搜索元素
- 将信息记录到控制台
- 将数据(与进度相关)添加到文本文件
如果开发人员决定使用新的日志库,他将不得不对方法实现进行更改。此外,如果他决定更改将数据保存在文本文件中的方式,他也必须对方法实现进行更改。
有什么方法可以避免这种情况吗?我的意思是,如果我找到了更好的方法(更好的算法)来找到列表中的元素,我只想对方法进行更改。在我看来,该算法不符合单一责任原则,它正在做的事情不止一件。
2条答案
按热度按时间r8uurelv1#
在我看来,该算法不符合单一责任原则,它正在做的事情不止一件。
正确的。这就是为什么对于日志记录、审计、安全检查、性能监视、异常处理、缓存、事务管理、持久性、验证等,即对于不同种类的附加正交行为,人们使用代码插装的原因之一
What are the possible AOP use cases?
插装可以是运行时(运行时反射、运行时注解、面向方面的编程、Java代理、字节码操作)、编译时(宏、编译时注解处理器、编译器插件)、预编译时/构建时(源代码生成、Scalameta/语义DB、SBT源代码生成器、样板模板)等。
例如,您可以在编译时使用macro annotation日志记录分支(“if-Else”)检测代码。
例如,Scastie仪器使用Scalameta用户输入的代码
https://github.com/scalacenter/scastie/tree/master/instrumentation/src/main/scala/com.olegych.scastie.instrumentation
在函数式编程中添加额外行为的另一种方法是效果,例如Monad。阅读关于记录Monad、
Writer
Monad、使用免费Monad进行记录等内容。cygmwpex2#
对于这个以意见为基础的问题,我将给出基于意见的回答。
有什么方法可以避免这种情况吗?
有一个解决方案,当然是通过算法。但您应该与我们分享以下代码:
你没有澄清你问题的以下部分:
“如果开发人员决定使用新的日志库...”
“此外,如果他决定更改数据在文本文件中的保存方式...”