ホームページ > バックエンド開発 > Python チュートリアル > 入れ子になったループで Python のクロージャ動作により予期しない結果が生じるのはなぜですか?

入れ子になったループで Python のクロージャ動作により予期しない結果が生じるのはなぜですか?

DDD
リリース: 2024-11-29 00:09:12
オリジナル
535 人が閲覧しました

Why Does Python's Closure Behavior Produce Unexpected Results in Nested Loops?

字句クロージャを理解する: Python のクロージャ動作を詳しく見る

字句クロージャの複雑さを詳しく調べると、Python コードの独特な動作が明らかになります。次の例を考えてみましょう:

flist = []

for i in xrange(3):
    def func(x): return x * i
    flist.append(func)

for f in flist:
    print f(2)
ログイン後にコピー

驚いたことに、このコードは、予期される "0 2 4" の代わりに "4 4 4" を出力します。この予期しない動作は、Python が字句クロージャを処理する方法に起因します。

反復ごとに新しいクロージャを作成する Perl とは異なり、Python は 3 つの個別の関数を作成します。ただし、各関数は、それが定義された環境、つまりグローバル環境のクロージャを保持します。この共有クロージャにより、すべての関数が同じ可変変数 i を参照することになり、予期しない出力が発生します。

この問題に対処するには、修正されたソリューションを採用する必要があります。関数クリエーターを導入し、ループ内でそれを呼び出すことで、一意の i 値を持つ関数ごとに個別の環境を作成します。

flist = []

for i in xrange(3):
    def funcC(j):
        def func(x): return x * j
        return func
    flist.append(funcC(i))

for f in flist:
    print f(2)
ログイン後にコピー

この改訂されたコードは問題を修正し、Python の動作方法における微妙だが重要な違いを示しています。 Perl は字句クロージャを処理します。使用されている特定のプログラミング言語のクロージャ動作を理解することで、開発者はそのような予期せぬ結果を回避し、より堅牢で予測可能なコードを作成できます。

以上が入れ子になったループで Python のクロージャ動作により予期しない結果が生じるのはなぜですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

ソース:php.cn
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート