python 在模块和类之间选择

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/600190/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-11-03 20:26:14  来源:igfitidea点击:

choosing between Modules and Classes

pythonoopmodule

提问by Xolve

In my application I have to maintain some global application state and global application wide methods like currently connected users, total number of answers, create an application config file etc. There are two options:

在我的应用程序中,我必须维护一些全局应用程序状态和全局应用程序范围的方法,例如当前连接的用户、答案总数、创建应用程序配置文件等。有两个选项:

  1. Make a separate appstate.py file with global variables with functions over them. It looks fine initially but it seems that I am missing somethingin clarity of my code.

  2. Create a class AppState with class functions in a appstate.py file, all other modules have been defined by their specific jobs. This looks fine. But now I have to write longer line like appstate.AppState.get_user_list(). Moreover, the methods are not so much related to each other. I can create separate classes but that would be too many classes.

  1. 创建一个单独的 appstate.py 文件,其中包含带有函数的全局变量。最初看起来不错,但似乎我在代码的清晰度方面遗漏了一些东西

  2. 在 appstate.py 文件中创建一个具有类函数的类 AppState,所有其他模块都由它们的特定作业定义。这看起来不错。但现在我必须写更长的行,如 appstate.AppState.get_user_list()。此外,这些方法彼此之间并没有太大的关联。我可以创建单独的类,但这样的类太多了。

EDIT: If I use classes I will be using classmethods. I don't think there is a need to instantiate the class to an object.

编辑:如果我使用类,我将使用类方法。我认为没有必要将类实例化为对象。

采纳答案by nosklo

The second approach seems better. I'd use the first one only for configuration files or something.

第二种方法似乎更好。我只会将第一个用于配置文件或其他东西。

Anyway, to avoid the problem you could always:

无论如何,为了避免这个问题,你总是可以:

from myapp.appstate import AppState

That way you don't have to write the long line anymore.

这样你就不必再写长线了。

回答by Jarret Hardie

Sounds like the classic conundrum :-).

听起来像经典的难题:-)。

In Python, there's nothing dirty or shameful about choosing to use a module if that's the best approach. After all, modules, functions, and the like are, in fact, first-class citizens in the language, and offer introspection and properties that many other programming languages offer only by the use of objects.

在 Python 中,如果这是最好的方法,那么选择使用模块并没有什么肮脏或可耻的。毕竟,模块、函数等实际上是该语言的一等公民,并提供许多其他编程语言仅通过使用对象才能提供的内省和属性。

The way you've described your options, it kinda sounds like you're not too crazy about a class-based approach in this case.

你描述你的选择的方式,在这种情况下,听起来你对基于类的方法并不太感冒。

I don't know if you've used the Django framework, but if not, have a look at the documentation on how it handle settings. These are app-wide, they are defined in a module, and they are available globally. The way it parses the options and expose them globally is quite elegant, and you may find such an approach inspiring for your needs.

我不知道您是否使用过 Django 框架,但如果没有,请查看有关它如何处理设置的文档。这些是应用程序范围的,它们在一个模块中定义,并且在全球范围内可用。它解析选项并在全局范围内公开它们的方式非常优雅,您可能会发现这种方法对您的需求很有启发。

回答by Devin Jeanpierre

The second approach is only significantly different from the first approach if you have application state stored in an instanceof AppState, in which case your complaint doesn't apply. If you're just storing stuff in a class and using static/class methods, your class is no different than a module, and it would be pythonic to instead actually have it as a module.

如果您将应用程序状态存储在AppState的实例中,则第二种方法与第一种方法只有显着不同,在这种情况下,您的投诉不适用。如果您只是在类中存储内容并使用静态/类方法,则您的类与模块没有什么不同,而实际上将其作为模块使用将是 Pythonic。

回答by MrTopf

Why not go with an instance of that class? That way you might even be able later on to have 2 different "sessions" running, depending on what instance you use. It might make it more flexible. Maybe add some method get_appstate()to the module so it instanciates the class once. Later on if you might want several instances you can change this method to eventually take a parameter and use some dictionary etc. to store those instances.

为什么不使用该类的实例?这样,您甚至可以稍后运行 2 个不同的“会话”,具体取决于您使用的实例。它可能会使其更加灵活。也许get_appstate()向模块添加一些方法,以便它实例化一次类。稍后,如果您可能需要多个实例,您可以更改此方法以最终获取一个参数并使用一些字典等来存储这些实例。

You could also use property decorators btw to make things more readable and have the flexibility of storing it how and where you want it stores.

顺便说一句,您还可以使用属性装饰器来使内容更具可读性,并可以灵活地存储它的存储方式和位置。

I agree that it would be more pythonic to use the module approach instead of classmethods.

我同意使用模块方法而不是类方法会更加 Pythonic。

BTW, I am not such a big fan of having things available globally by some "magic". I'd rather use some explicit call to obtain that information. Then I know where things come from and how to debug it when things fail.

顺便说一句,我不太喜欢通过某种“魔法”在全球范围内提供东西。我宁愿使用一些显式调用来获取该信息。然后我知道事情从哪里来,以及当事情失败时如何调试它。

回答by Roman Glass

Consider this example:

考虑这个例子:

configuration
|
+-> graphics
|   |
|   +-> 3D
|   |
|   +-> 2D
|
+-> sound

The real question is: What is the difference between classes and modules in this hierarchy, as it could be represented by both means?

真正的问题是:这个层次结构中的类和模块之间有什么区别,因为它可以用两种方式表示?

Classes represent types. If you implement your solution with classes instead of modules, you are able to check a graphics object for it's proper type, but write generic graphics functions.

类代表类型。如果您使用类而不是模块来实现您的解决方案,您可以检查图形对象的正确类型,但编写通用图形函数。

With classes you can generate parametrized values. This means it is possible to initialize differently the soundsclass with a constructor, but it is hard to initialize a module with different parameters.

使用类,您可以生成参数化值。这意味着可以使用构造函数以不同的方式初始化声音类,但很难使用不同的参数初始化模块。

The point is, that you really something different from the modeling standpoint.

关键是,从建模的角度来看,您确实有所不同。

回答by Andrew Hare

I would go with the classes route as it will better organize your code. Remember that for readability you can do this:

我会选择类路线,因为它会更好地组织您的代码。请记住,为了可读性,您可以这样做:

from appstate import AppSate

回答by rotoglup

I'd definitely go for the second option : having already used the first one, I'm now forced to refactor, as my application evolved and have to support more modular constructs, so I now need to handle multiple simulataneous 'configurations'.

我肯定会选择第二个选项:已经使用了第一个选项,我现在被迫重构,因为我的应用程序不断发展并且必须支持更多的模块化结构,所以我现在需要处理多个同时的“配置”。

The second approach is, IMO, more flexible and future proof. To avoid the longer lines of code, you could use from appstate import AppStateinstead of just import appstate.

第二种方法是 IMO,更灵活且面向未来。为了避免较长的代码行,您可以使用from appstate import AppState而不仅仅是import appstate.