“自我”在哪里?来自?将成员函数作为 threading.Thread 的目标

发布于 2024-12-10 03:54:44 字数 497 浏览 0 评论 0原文

在下面的代码中,

class foo:
    def __init__(self,x):
        self.x = x

    def do(self):
        print(self.x)

foo1 = foo(1)
foo2 = foo(2)
t1=threading.Thread(target=foo1.do)
t2=threading.Thread(target=foo2.do)
t1.start()
t2.start()

我使用实例化对象的成员函数作为线程的目标。我想知道它为什么起作用,即线程模块是否做了一些特殊的事情来检测在另一端是否有一个 member 函数(而不是一个没有对象上下文的“正常”函数)可调用参考?我认为 ftplib.retrlines() 等中的常用回调机制仅接受普通的全局函数。是不是最好完全远离这个?

slarti

PS:来自 C/C++ 的暴露行为对我来说是新的(尽管欢迎)。

in the following code

class foo:
    def __init__(self,x):
        self.x = x

    def do(self):
        print(self.x)

foo1 = foo(1)
foo2 = foo(2)
t1=threading.Thread(target=foo1.do)
t2=threading.Thread(target=foo2.do)
t1.start()
t2.start()

I am using the member function of an instantiated object as target for the thread. I was wondering why it works, i.e. does the threading module do something special to detect if there is a member function (as opposed to a "normal" function w/o object context) at the other end of the callable-Reference? I think the usual callback mechanism like in ftplib.retrlines() et al will only accept plain global functions. Is it better to stay away from this alltogether?

slarti

PS: coming from C/C++ the exposed behaviour is new to me (although welcome).

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

沧笙踏歌 2024-12-17 03:54:45

foo1.dofoo2.do 是绑定方法。

我建议您查看以下文档链接:

第二个链接摘录:

当调用绑定的用户定义方法对象时,底层
调用函数 (im_func),插入类实例 (im_self)
在参数列表前面。例如,当 C 是一个类时,
包含函数 f() 的定义,x 是 C 的实例,
调用 xf(1) 相当于调用 Cf(x, 1)。

foo1.do and foo2.do are bound methods.

I suggest you look at the following documentation links:

Excerpt from the second link:

When a bound user-defined method object is called, the underlying
function (im_func) is called, inserting the class instance (im_self)
in front of the argument list. For instance, when C is a class which
contains a definition for a function f(), and x is an instance of C,
calling x.f(1) is equivalent to calling C.f(x, 1).

暮年 2024-12-17 03:54:45

假设您用 C++ 编写了同一个类:

class foo {
    int x;
  public:
    foo(int x_) { x = x_; }
    void do() { std::cout << x; }
}

foo f = foo(42);

这里 &foo::do 将是指向成员函数的指针,您需要一个 foo 实例才能调用它。假设您可以传递 f.do: 那么您不需要任何其他东西来调用 f 上的 do()。这正是 Python 中绑定成员的含义,通过传递 foo1.do ,您将传递要调用的方法和要调用它的实例。

同样的问题在 C++ 中已经通过专有扩展(例如 Borland 的闭包)或库(例如 Boost.Bind

Suppose you wrote the same class in C++:

class foo {
    int x;
  public:
    foo(int x_) { x = x_; }
    void do() { std::cout << x; }
}

foo f = foo(42);

Here &foo::do would be a pointer to member function and you would need a foo instance to be able to call it. Suppose you could pass around f.do: then you wouldn't need anything else to call do() on f. This is exactly what a bound member is in Python and by passing foo1.do you are passing both the method to call and the instance onm which to call it.

This same problem has been addressed in C++ either with proprietary extensions, such as Borland's closures, or with libraries, such as Boost.Bind.

迷途知返 2024-12-17 03:54:45

在类中的任何实例(非静态)方法中,该方法应该使用其运行所在的类实例中的一些变量,对吗?因此,每个实例方法都需要运行它的对象的副本才能访问这些变量。这就是self,即运行该方法的对象的副本。

在大多数语言中,它在实例方法中隐式地是一个参数(所以你实际上不需要在方法中写出 self ,但它在那里 ,但在 python 中它是显式显示的,所以你在每个实例方法中都有一个名为self` 的参数,它不会改变任何内容,它只是显示正在发生的情况的一种更明显的方式。

In any instance (non-static) method in a class, the method should be using some variables in the instance of the class thats its running in right? So, every instance method needs a copy the object thats running it to access these variables. That is what self is, a copy of the object thats running the method.

In most languages, its implicitly a parameter in instance methods (so you don't really need to write out self in the method, but its there, but in python its explicitly shown, so you have a parameter calledself` in every instance method. It does not change anything, it's just a sort of more obvious way of showing whats happening.

笑咖 2024-12-17 03:54:44

您可能想了解 Python 的方法对象

Python 的 self 有点像 C++ 的 this ,只不过您必须将其放在方法声明中。

当您在类中声明一个函数时,它会“变成”一个方法,会发生什么情况。当您获取对象的方法时,它就成为绑定方法,其中第一个参数(self)固定为您从中获取它的对象。

尝试:

class Foo(object):
    def do(self):
        print x

instance = Foo()
print Foo.do  # prints <unbound method Foo.do>
print instance.do  # prints <bound method Foo.do of <...>>

# These are equivalent:
Foo.do(instance)
instance.do()

在你的线程案例中没有发生额外的魔法,它只是普通的Python。

You might want to read about Python's method objects.

Python's self is sort of like C++'s this, except you have to put it in the method declaration.

What happens that when you declare a function inside a class, it “becomes” a method. When you get a method of an object, it becomes a bound method, which has the first argument (self) fixed to the object you got it from.

Try:

class Foo(object):
    def do(self):
        print x

instance = Foo()
print Foo.do  # prints <unbound method Foo.do>
print instance.do  # prints <bound method Foo.do of <...>>

# These are equivalent:
Foo.do(instance)
instance.do()

No extra magic is happening in your Threading case, it's just regular Python.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文