谁持有对乔的引用?用于析构函数/清理的 Pythonic 方法?

XOp*_*lay 2 python

我有以下 Python 代码:

#!/usr/bin/python3

import time

class Greeter:
    def __init__(self, person):
        self.person = person
        print("Hello", person);

    def __del__(self):
        print("Goodbye", self.person);

    def inspect(self):
        print("I greet", self.person);

if __name__ == '__main__':
    to_greet = []
    try:
        to_greet.append(Greeter("world"));
        to_greet.append(Greeter("john"));
        to_greet.append(Greeter("joe"));

        while 1:
            for f in to_greet:
                f.inspect()
            time.sleep(2)

    except KeyboardInterrupt:
        while (len(to_greet) > 0):
            del to_greet[0]
        del to_greet
        print("I hope we said goodbye to everybody. This should be the last message.");
Run Code Online (Sandbox Code Playgroud)

当我运行它并Ctrl+C在睡眠期间,我得到:

Hello world
Hello john
Hello joe
I greet world
I greet john
I greet joe
^CGoodbye world
Goodbye john
I hope we said goodbye to everybody. This should be the last message.
Goodbye joe
Run Code Online (Sandbox Code Playgroud)

我不明白为什么Goodbye joe只在This should be the last message. 谁持有对它的引用?是print声明吗?即使我放在gc.collect()最后一个之前,print我也没有看到我们在最后一个之前向乔说再见print。我怎样才能强迫它?

从我一直在谷歌上搜索的内容来看,似乎我应该with在这种情况下使用该语句,但是当要问候的人数可变时(例如,从 names.txt 文件中读取),我不确定如何实现这一点) 或只是大。

似乎我无法C++在 Python 中获得类似的析构函数,那么实现这样的析构函数的最惯用和优雅的方法是什么?我不一定需要删除/销毁对象,但我确实需要保证我们绝对向所有人说再见(除了例外,被信号杀死等)。理想情况下,我想用最优雅的代码来做到这一点。但就目前而言,抗异常应该没问题。

use*_*ica 7

它是f。循环变量不在循环范围内;在 Python 中创建新作用域的唯一语法结构是类、函数、推导式和生成器表达式。

f一直存活到解释器关闭。虽然当前的 CPython 实现试图在解释器关闭时清理模块内容,但我认为这在任何地方都没有得到承诺。