Python、__init__ 和自我困惑
好吧,当我看到这个时,我正在查看一些来源:
>>> def __parse(self, filename):
... "parse ID3v1.0 tags from MP3 file"
... self.clear()
... try:
... fsock = open(filename, "rb", 0)
... try:
... fsock.seek(-128, 2)
... tagdata = fsock.read(128)
... finally:
... fsock.close()
... if tagdata[:3] == 'TAG':
... for tag, (start, end, parseFunc) in self.tagDataMap.items():
... self[tag] = parseFunc(tagdata[start:end])
... except IOError:
... pass
...
所以,我决定对其进行测试。
>>> __parse("blah.mp3")
而且,我收到了这个错误:
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: __parse() takes exactly 2 arguments (1 given)
这不是我第一次遇到这个问题,我一直认为我应该将 self 包含在参数参数列表中,但我知道这是不对的。 有人可以向我解释为什么这种情况在我尝试使用的代码中经常发生吗?我想这是由于我对这些术语的理解程度所致,我什至几乎不明白 init 或 self 的作用,或者为什么它是相关的。 def x(b): print b 与 def x(self, b): self.b = b print self.b 相同,不是吗? 为什么它如此重要!
我只是想要一个基本的解释,这样我就可以摆脱这个问题,谢谢。
Alright, so I was taking a look at some source when I came across this:
>>> def __parse(self, filename):
... "parse ID3v1.0 tags from MP3 file"
... self.clear()
... try:
... fsock = open(filename, "rb", 0)
... try:
... fsock.seek(-128, 2)
... tagdata = fsock.read(128)
... finally:
... fsock.close()
... if tagdata[:3] == 'TAG':
... for tag, (start, end, parseFunc) in self.tagDataMap.items():
... self[tag] = parseFunc(tagdata[start:end])
... except IOError:
... pass
...
So, I decided to test it out.
>>> __parse("blah.mp3")
And, I received this error:
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: __parse() takes exactly 2 arguments (1 given)
This wouldn't be the first time I've encountered this, I keep thinking I'm meant to include self in the argument parameter list, but I know that that's not right. Could someone explain to me why this happens a lot with code I try to play around with, I suppose its due to my level of understanding about the terms, I barely even understand what init or self does, or why it's relevant. def x(b): print b is the same as def x(self, b): self.b = b print self.b isn't it? Why does it matter so much!
I just want a basic explanation, so I can get this out of my mind,thanks.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(5)
def __parse 位于某个类定义中。
您无法将方法定义从类定义中提取出来。 方法函数定义是类的一部分。
看这两个例子:
和
注释。
该函数不使用
self
。类方法确实使用了
self
。 一般来说,所有实例方法都会使用self
,除非它们有特定的装饰器,例如@classmethod
另有说明。该函数不依赖于其他任何东西。
类方法取决于由类
Adder
的实例调用; 此外,它还取决于 Adder 类的实例是否已正确初始化。 在这种情况下,初始化函数 (__init__
) 确保Adder
的每个实例始终具有一个名为grand_total
的实例变量,并且该实例变量具有初始值为0
。您无法将
add
方法函数从Adder
类中取出并单独使用。 它不是一个独立的功能。 它是在类内部定义的,并且由于类内部的位置而具有一定的期望。The
def __parse
was inside some class definition.You can't pull the method defs out of the class definitions. The method function definition is part of the class.
Look at these two examples:
And
Notes.
The function does not use
self
.The class method does use
self
. Generally, all instance methods will useself
, unless they have specific decorators like@classmethod
that say otherwise.The function doesn't depend on anything else else.
The class method depends on being called by an instance of the class
Adder
; further, it depends on that instance of the classAdder
having been initialized correctly. In this case, the initialization function (__init__
) has assured that each instance ofAdder
always has an instance variable namedgrand_total
and that instance variable has an initial value of0
.You can't pull the
add
method function out of theAdder
class and use it separately. It is not a stand-alone function. It was defined inside the class and has certain expectations because of that location inside the class.函数/方法可以在类之外编写,然后用于 Python 中称为 monkeypatching 的技术:
Functions/methods can be written outside of a class and then used for a technique in Python called monkeypatching:
看起来您对类和面向对象编程有点困惑。 对于来自其他编程语言的人来说,“自我”是 Python 中的陷阱之一。 IMO 官方教程处理得不太好。 这个教程看起来相当不错。
如果你学过java,Python中的
self
与java中的this
非常相似。 不同之处在于 python 要求您将 self 列为类定义中每个函数的第一个参数。如果 python 是您的第一种编程语言(或您的第一种面向对象的语言),您可以记住这是一个简单的经验法则:如果您定义的函数是类的一部分,则需要包含
self
作为第一个参数。 如果您定义的函数不属于类的一部分,则不应在参数中包含self
。 如果不做一些(或可能很多)额外的编码,就不能将类函数使其独立。 最后,在调用函数时,切勿将self
作为参数。这些规则也有例外,但现在不值得担心。
Looks like you're a bit confused about classes and object-oriented programming. The 'self' thing is one of the gotchas in python for people coming from other programming languages. IMO the official tutorial doesn't handle it too well. This tutorial seems quite good.
If you've ever learnt java,
self
in python is very similar tothis
in java. The difference is that python requires you to listself
as the first argument to every function in a class definition.If python is your first programming language (or your first object-oriented language), you could remember this as a simple rule-of-thumb: if you're defining a function that's part of a class, you need to include
self
as the first argument. If you're defining a function that's not part of a class, you shouldn't includeself
in the arguments. You can't take a class function and make it stand-alone without doing some (or possibly a lot of) extra coding. Finally, never includeself
as an argument when calling a function.There are exceptions to those rules, but they're not worth worrying about now.
self 由类上的实例方法包装器自动传入。 这个函数没有被包装; 它不是一个方法,它只是一个函数。 如果不附加到类,它甚至没有意义,因为它需要 self 参数。
self is passed in automatically by the instancemethod wrapper on classes. This function isn't wrapped; it's not a method, it's just a function. It doesn't even make sense without being attached to a class, since it needs the self parameter.
顺便说一句,在 Python 中创建类的静态方法是可能的。 最简单的方法是通过装饰器(例如
@staticmethod
)。 我怀疑这种事情通常不是Python式的解决方案。As an aside, it is possible to create static methods of a class in Python. The simplest way to do this is via decorators (e.g.
@staticmethod
). I suspect this kind of thing is usually not the Pythonic solution though.