目次
高階関数
変数は関数を指すことができ、関数自体も変数に割り当てることができます。つまり、変数は関数を指すことができます。
>>> f = abs
>>> f(-10)
10
関数名も変数です。関数名は実際には関数を指す変数です。
関数は別の関数をパラメーターとして受け取ることができます。この関数は高階関数と呼ばれます。
#一个最简单的高阶函数:
def add(x, y, f):
return f(x) + f(y)
上記の関数を呼び出すときの派生プロセスは次のとおりです。
x = -5
y = 6
f = abs
f(x) + f(y) ==> abs(-5) + abs(6) ==> 11
return 11
map / reduce
map()
関数は、1つの関数であり、2つのパラメータを受け取り、他方はであるIterable
ためにmap
順番に配列の各要素に渡された関数を適用し、新しいものとして結果を返しますIterator
。
>>> def f(x):
... return x * x
...
>>> r = map(f, [1, 2, 3, 4, 5, 6, 7, 8, 9])
>>> list(r)
[1, 4, 9, 16, 25, 36, 49, 64, 81]
map()
渡される最初のパラメーターf
は、関数オブジェクト自体です。結果r
は1Iterator
であるためIterator
、レイジーシーケンスです。したがって、list()
関数を使用してシーケンス全体を計算し、リストを返します。
reduce(function、sequence、initializer = None)は、関数をシーケンスに適用します[x1, x2, x3, ...]
。この関数は2つのパラメーターを受け取る必要がありreduce
、結果はシーケンスの次の要素で引き続き累積されます。
- オプションのパラメータ初期化子が提供されている場合、それをシーケンスの要素としてシーケンスの最初の部分に挿入するのと同じです。
効果は次のとおりです。
たとえば、シーケンスを合計するには、次のようにします。
>>> from functools import reduce
>>> def add(x, y):
... return x + y
>>> reduce(add, [1, 3, 5, 7, 9])
25
str
上記の例を少し変更して、文字列もシーケンスであると考えると、次のように変換する関数をmap()
記述できます。str
int
>>> from functools import reduce
>>> def fn(x, y):
... return x * 10 + y
>>> def char2num(s):
... digits = {'0': 0, '1': 1, '2': 2, '3': 3, '4': 4, '5': 5, '6': 6, '7': 7, '8': 8, '9': 9}
... return digits[s]
>>> reduce(fn, map(char2num, '13579'))
13579
1つに編成されたstr2int
機能は次のとおりです。
from functools import reduce
DIGITS = {'0': 0, '1': 1, '2': 2, '3': 3, '4': 4, '5': 5, '6': 6, '7': 7, '8': 8, '9': 9}
def str2int(s):
def fn(x, y):
return x * 10 + y
def char2num(s):
return DIGITS[s]
return reduce(fn, map(char2num, s))
ラムダ関数を使用して、さらに単純化することもできます。
from functools import reduce
DIGITS = {'0': 0, '1': 1, '2': 2, '3': 3, '4': 4, '5': 5, '6': 6, '7': 7, '8': 8, '9': 9}
def char2num(s):
return DIGITS[s]
def str2int(s):
return reduce(lambda x, y: x * 10 + y, map(char2num, s))
filter(
関数、反復可能)
シーケンスのフィルタリングに使用されます
filter()
また、関数とシーケンスを受け取ります。map()
差があることがfilter()
渡された関数は、順番に各要素に作用し、その後決定True
するかどうかFalse
の要素を維持するか破棄する戻り値に応じ。空の文字列を順番に削除するには、次のように記述します。
def not_empty(s):
return s and s.strip()
list(filter(not_empty, ['A', '', 'B', None, 'C', ' ']))
# 结果: ['A', 'B', 'C']
フィルタを使用して素数を見つける
素数を計算する1つの方法はEhrlichSieve法であり、そのアルゴリズムは非常に簡単に理解できます。
まず、2
シーケンスを構築するために最初からすべての自然数をリストします:2、3、4、5、6、7、8、9、10、11、12、13、14、15、16、17、18、19、 20、..。
シーケンスの最初の数をとり2
、それが素数でなければならず、その後の倍数除外2
シーケンス2
:3、 4、5、 6、 7、 8、9、 10、11、 12、13、 14、 15 、 16、 17、 18、19、 20、新しいシーケンスの最初の数をとり3
、それが素数であり、その後しなければならないの倍数除外3
シーケンス3
:5、 6、7、8、 9、10、11 、 12、13、14、 15、16、17、 18、19、20、...新しいシーケンスの最初の数を取り5
、その後の倍数除外5
シーケンスを5
:7、8、9、 10、11 、12、13、14、 15、 16、17、18、19、 20、...ダウンふるい分けてください、あなたはすべての素数を得ることができます。
def _odd_iter(): #构造一个从3开始的奇数序列
n = 1
while True:
n = n + 2
yield n
def _not_divisible(n): #定义一个筛选函数
return lambda x: x % n > 0
def primes(): #定义一个生成器,不断返回下一个素数
yield 2
it = _odd_iter() # 初始序列
while True:
n = next(it) # 返回序列的第一个数
yield n
it = filter(_not_divisible(n), it) # 构造新序列
# 打印1000以内的素数:
for n in primes():
if n < 1000:
print(n)
else:
break
ソート済み
sorted()
関数も高階関数であり、key
絶対値による並べ替えなど、カスタム並べ替えを実現する関数を受け取ることもできます。
>>> sorted([36, 5, -12, 9, -21], key=abs)
[5, 9, -12, -21, 36]
ASCII比較のサイズに従って、文字列 を並べ替える
学生の名前と成績を表すためにタプルのセットを使用するとします。
L = [('Bob', 75), ('Adam', 92), ('Bart', 66), ('Lisa', 88)]
sorted()
上記のリストを名前で並べ替える場合に使用します。
L = [('Bob',75), ('Admin', 92), ('Bart', 66), ('List', 88)]
def by_name(t):
return t[0].lower()
L2 = sorted(L, key=by_name)
print(L2)
タプルのリストの並べ替えタプル
のセットを使用して名前と年齢を表し、sorted()関数を使用して名前を昇順で並べ替え、年齢を降順で並べ替えるとします。
def sort_by_name(t):
return t[0]
def sort_by_age(t):
return t[1]
L = [('Tom', 18), ('Jerry', 15), ('Peter', 16), ('John', 20)]
list1 = sorted(L, key=sort_by_name)
list2 = sorted(L, key=sort_by_age, reverse=True)
print('sort by name asc: ', list1)
print('sort by age desc: ', list2)
出力結果:
sort by name asc: [('Jerry', 15), ('John', 20), ('Peter', 16), ('Tom', 18)]
sort by age desc: [('John', 20), ('Tom', 18), ('Peter', 16), ('Jerry', 15)]
例4:辞書の内容を並べ替える
辞書を並べ替える方法はたくさんありますが、基本的な考え方は同じです。つまり、dictのキー、値、またはアイテムをリストに分けてから、リストを並べ替えて、間接的にdictを並べ替えます。
D = {'Tom': 18, 'Jerry': 15, 'Peter': 16, 'John': 20}
list1 = sorted(D.items(), key=lambda d: d[0])
list2 = sorted(D.items(), key=lambda d: d[1], reverse=True)
print('sort by key asc:', list1)
print('sort by value desc:', list2)
出力結果:
sort by key asc: [('Jerry', 15), ('John', 20), ('Peter', 16), ('Tom', 18)]
sort by value desc: [('John', 20), ('Tom', 18), ('Peter', 16), ('Jerry', 15)]