はい、あなたの観察は正しいです。これは、バインディングが Python で機能する方法の結果です。
するとき
import foo
foo
は、モジュールを参照するグローバル名になりますfoo
。するとき
foo.bar = 7
次に、参照が追跡され、オブジェクトfoo
がロードされます。その後7
、属性に格納されbar
ます。
別のモジュールが をインポートfoo
すると、オブジェクトが取り出されsys.modules['foo']
、変更された値が取得されます。
するとき
from foo import bar
globals()['bar']
参照に設定されていますfoo.bar
。後で行うとき
bar = 7
globals()['bar']
はもはや参照していませんfoo.bar
が、 のコピーを参照しています7
。つまり、インポート モジュールのグローバル スコープ内の元のバインディングは単純に置き換えられます。
最初の例では、格納されているオブジェクトの属性を変更してsys.modules
おり、それをインポートしたすべてのモジュールに共通です。2 番目の例では、インポート モジュールのグローバル スコープを変更しています。
の線に沿って何かをする場合
from foo import fobaz
fobaz.foobar = 7
次に、グローバル参照を上書きするのではなく、それに従って、それが指すオブジェクトの属性を変更するため、その変更は他のインポートモジュールに伝播されます。基本的に、グローバルバインディングを上書きしない限り、変更可能なオブジェクトを変更できるはずです。
このようなものは、Pythonで真のグローバルにきれいに到達できる最も近いものだと思います。言語として、名前空間を非常に重視しています。