是不是 "Python-esque" 把所有函数都包在一个 class 里?

Is It "Python-esque" to wrap all functions in a class?

所以,我现在正在 Python 开发一个简单的网络抓取工具,但我对如何构建我的代码有疑问。在其他编程语言中(尤其是 C++ 和 C# 等编译语言),我习惯于将所有函数包装在 classes 中。 IE。在我的网络抓取示例中,我可能会有一个名为 "WebScraper" 的 class,然后在 class 中包含所有函数。如果我需要实例化原始 "WebScraper" class.

的多个实例,我什至可能会创建第二个助手 class,例如 "WebScraperManager"

不过,这引出了我当前的问题。类似的逻辑在当前示例中是否成立?或者我会简单地定义一个 WebScraper.py 文件,在该文件中没有包装器 class,然后将我需要的函数导入到某个 main.py 文件中吗?

你的意思是“pythonic”。

这取决于您想要实现的面向对象、可扩展性……的程度。我会在简单的函数上使用 class。让我们说明天你想要一个 CraiglistScraper 和一个 FacebookScraper... 我会创建一个抽象 class "Scraper ” 然后上面两个继承自这个并重新实现你需要的(多态性)。我的意思是面向对象的原则和模式是独立于语言的。现在我不会在class(单一责任原则)中“持有所有功能”,每次你编码时记住这个词“SOLID”。

class 和函数 的区别应该 是 class 有状态。一些 classes 没有状态,但这很少是一个好主意(我确定有例外,例如抽象基础 classes (ABCs) 但我不确定它们是否重要),有些函数确实有状态,但这很少是一个好主意(缓存或检测可能是例外)。

如果您想要一个 URL 作为输入,并说一个字典作为输出,然后您就完成了该网站,则没有理由使用 class。只需要一个接受 URL 和 returns 字典的函数。无状态函数是比 classes 更简单的抽象,因此在所有其他条件相同的情况下,更喜欢它们。

但是,很多时候可能会涉及到中间状态。例如,也许您正在 抓取 植根于基础 URL 的一系列页面,急切地完成所有这些工作太昂贵了。也许那么你想要的是一个 class 以根 URL 作为其构造函数。然后它有一些方法来查询它可以跟进哪些 child URLs,以及订购后续抓取 children 的方法,这些数据可能存储在嵌套数据结构中。

当然,如果您的任务相当复杂,您的层可能会使用 classes 或 classes 调用函数。但是持久化状态是一个很好的指示器,表明即时任务应该写成 class 还是函数集。

编辑:只是为了结束循环并回到最初的问题:不,我会说将所有函数包装在 classes 中不是 pythonesque。自由函数在 python 中很好,这完全取决于什么是合适的。此外,pythonesque 一词不是很 pythonic ;-)