ホームページ >バックエンド開発 >Python チュートリアル >Python のラムダ匿名関数の簡単な紹介

Python のラムダ匿名関数の簡単な紹介

WBOY
WBOYオリジナル
2016-06-16 08:46:341150ブラウズ

Lambda 関数は匿名関数とも呼ばれます。つまり、関数には特定の名前がありません。まず最も単純な例を見てみましょう:

コードをコピー コードは次のとおりです:

def f(x):
return x**2
print f(4)

Python でラムダを使用する場合は、次のように記述します
コードをコピー コードは次のとおりです:

g = lambda x : x**2
print g(4)

ラムダ式には、多くのプログラミング言語で対応する実装があります。たとえば、C#:

コードをコピーします コードは次のとおりです。

var g = x =>** 2
Console .WriteLine(g(4))

それでは、ラムダ式はどのように使用されるのでしょうか?通常の関数と比較して、lambda は関数名を省略するだけですが、そのような匿名関数を他の場所で共有したり呼び出すことはできません。実際、その通りです。ラムダは Python のような動的言語では驚愕的な役割を果たしません。ラムダに代わるメソッドが他にもたくさんあるからです。同時に、lambda を使用した記述方法は、あまり Python らしくないように見えることもあります。将来の Python バージョンではラムダをキャンセルすることを提案する人もいます。

振り返って考えてみると、Python のラムダは本当に役に立たないのでしょうか?実際にはいいえ、少なくとも私が思いつくのは次のとおりです:

1. Python を使用して実行スクリプトを作成する場合、ラムダを使用すると関数を定義するプロセスが省略され、コードがより合理化されます。

2. 他の場所で再利用されない一部の抽象関数の場合、ラムダを使用する場合、名前付けの問題を考慮する必要はありません。

3. 特定の場面でコードを理解しやすくするためにラムダを使用します。

Lambda の基本
ラムダ ステートメントでは、コロンの前にパラメータがあり、カンマで区切って複数のパラメータを指定することができ、コロンの右側に戻り値を指定します。ラムダ ステートメントが実際に構築するのは関数オブジェクトです:

コードをコピーします コードは次のとおりです:

g = lambda x: x**2
print g
at 0x00AFAAF0>

C# 3.0 からはラムダ式も追加され、面倒な処理が不要になりました。 delegate を使った書き方。 C# のラムダ式キーワードは => です。次の例を見てください:
コードをコピーします コードは次のとおりです:

var array = new int[] {2, 3, 5, 7, 9};
var result = array.Where(n => n > 3) // [5, 6, 9]; ]


C# では拡張メソッドを使用するため、配列オブジェクトに Where や Sum などの便利なメソッドが追加されます。 Python には、filter、map、reduce など、使いやすい明確に定義されたグローバル関数もいくつかあります。
コードをコピー コードは次のとおりです。

>>> foo = [2, 18, 9, 22, 17 , 24, 8, 12, 27]
>>>
>>> 印刷フィルター(lambda x: x % 3 == 0, foo)
[18 , 9, 24, 12, 27]
>>>
>>> マップを印刷(ラムダ x: x * 2 + 10, foo)
[14, 46, 28 , 54, 44, 58, 26, 34, 64]
>>>
>>> printreduce(lambda x, y: x + y, foo)
139

それはラムダでなければなりませんか?
上記の例のマップの機能は、C# の Where 拡張メソッドと同じであり、非常にシンプルで便利です。しかし、Python はそのような単純さを実現するためにラムダを使用する必要があるのでしょうか?オブジェクト トラバーサル処理の観点から見ると、Python の for..in..if 構文は実際には非常に強力で、ラムダよりも読みやすいです。たとえば、上記のマップの例は次のように記述できます:

コードをコピー コードは次のとおりです:

print [x * foo の x は 2 + 10]

非常に簡潔でわかりやすい。フィルターの例は次のように記述できます:
コードをコピー コードは次のとおりです:

print [x for x in foo if x % 3 = = 0]

もラムダメソッドより理解しやすいです。

したがって、ラムダをいつ使用するのか、いつ使用しないのか、表現された意図が明確である限り、具体的な状況を分析する必要があります。一般に、for..in..if でそれができるのであれば、私はラムダを選択しません。

ラムダが壊れていますか?
数学の教育では、ラムダがよく使用されます。たとえば、ある兄弟はこのような問題に遭遇しました。彼は、関数配列 fs=[f0,...,f9] (fi(n)=i+n) を作成したいと考え、次のようなラムダ関数を定義しました。コード

コードは次のとおりです: fs = [(lambda n: i + n) for i in range(10)]
しかし、奇妙なのは、


コードをコピー
コードは次のとおりです:>>> [3](4)13>fs[4](4)
13
>fs[5](4)
13


結果はこの人の期待を満たしていませんでした。期待された結果は次のようになります。
コードをコピーします コードは次のとおりです:

>>> fs[3](4)
7
>>> fs[4](4)
8
>>> fs[5 ](4)
9

問題は実際には変数 i にあります。上記のコードをラムダを使用しない単純な短縮バージョンに変更します:
コードをコピーします コードは次のとおりです:

i = 1
def fs(n):
return n + i
print fs(1) # 2
i = 2
print fs(1) # 3

visible 、上記が期待を満たさない理由は、lambda の i が匿名関数の外側のグローバル変数を使用しているためです。変更します:
コードをコピーします コードは次のとおりです:

fs = [(lambda n, i=i : i + n) for i in range(10)]
>7
>
>8
>>> fs[5](4)
9

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