ホームページ >バックエンド開発 >Python チュートリアル >ループ内の Lambda 関数が各反復の値ではなく最後の値を取得するのはなぜですか?

ループ内の Lambda 関数が各反復の値ではなく最後の値を取得するのはなぜですか?

Susan Sarandon
Susan Sarandonオリジナル
2024-12-21 07:52:10423ブラウズ

Why Do Lambda Functions in Loops Capture the Last Value Instead of Each Iteration's Value?

ループ内のラムダ

次のコード スニペットを考えてみましょう:

# directorys == {'login': <object at ...>, 'home': <object at ...>}
for d in directorys:
    self.command["cd " + d] = (lambda : self.root.change_directory(d))

目標は、キーを持つ 2 つの関数の辞書を作成することです。 「CD ログイン」と「CD ホーム」。ただし、結果は、両方のラムダ関数がキー「cd login」を持つ同じ内容を持っていることを示しています。

この予期しない動作を理解するには、入れ子になったループでラムダ関数がどのように動作するかを考慮することが重要です。ラムダ関数がループ内で定義されると、周囲のスコープから変数をキャプチャします。この場合、ループからの変数 d は各ラムダ関数によってキャプチャされます。

ただし、ラムダ関数は遅延実行されます。したがって、ループの外側で self.command ディクショナリにアクセスすると、すべてのラムダ関数が同じ d 変数、つまりループ内の d の最後の値をキャプチャします。したがって、すべての関数が同じメソッドを指し、観察される動作が生じます。

この問題を解決するには、各ラムダ関数が d の個別の値を確実に取得する必要があります。解決策の 1 つは、d をパラメータとしてラムダ関数に渡し、デフォルト値を指定することです。

lambda d=d: self.root.change_directory(d)

これで、ラムダ関数内の d は、同じ名前であってもパラメータを使用します。このパラメータのデフォルト値は関数の作成時に評価され、ループの反復ごとに d の正しい値にバインドされます。

または、ネストされたクロージャを使用して同じ結果を達成することもできます。

(lambda d: lambda: self.root.change_directory(d))(d)

以上がループ内の Lambda 関数が各反復の値ではなく最後の値を取得するのはなぜですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。