Python: Почему functools.partial необходимый?

Частичное приложение прохладно. Что делает функциональность functools.partial предложение, что Вы не можете пройти через лямбды?

>>> sum = lambda x, y : x + y
>>> sum(1, 2)
3
>>> incr = lambda y : sum(1, y)
>>> incr(2)
3
>>> def sum2(x, y):
    return x + y

>>> incr2 = functools.partial(sum2, 1)
>>> incr2(4)
5

functools так или иначе более эффективный, или читаемый?

183
задан DomQ 15 June 2013 в 00:28
поделиться

3 ответа

Вот пример, который показывает разницу:

In [132]: sum = lambda x, y: x + y

In [133]: n = 5

In [134]: incr = lambda y: sum(n, y)

In [135]: incr2 = partial(sum, n)

In [136]: print incr(3), incr2(3)
8 8

In [137]: n = 9

In [138]: print incr(3), incr2(3)
12 8

Эти сообщения Ивана Мура расширяют «ограничения лямбда-выражения» и замыкания в python:

75
ответ дан 23 November 2019 в 06:00
поделиться

Какие функции functools.partial предложение, которое вы не можете пройти через лямбды?

Не так много с точки зрения дополнительных функциональных возможностей (но, см. ниже) - и удобочитаемость в глазах смотрящего.
Большинству людей, знакомых с функциональными языками программирования (в частности, из семейств Lisp / Scheme), похоже, очень нравится лямбда - я говорю «большинство», определенно не все, потому что мы с Гвидо, несомненно, являемся одними из тех, кто "знаком с" (и т. д.), но думаем о лямбда как о бредовой аномалии в Python ...
Он раскаивался в том, что когда-либо принимал его в Python, хотя планировал удалить его из Python 3, как один из «сбоев Python».
Я полностью его в этом поддержал. (Мне нравится лямбда в схеме ... в то время как его ограничения в Python , и странный способ, которым он просто не вписывается в с остальными) языка, заставьте мою кожу ползать мурашками).

Однако не так для толпы любителей лямбда , которые устроили один из самых близких к восстанию событий в истории Python, пока Гвидо не отступил и не решил оставить лямбда дюймов
Несколько возможных дополнений к functools (для создания функций, возвращающих константы, идентификационные данные и т. Д.) Не произошло (чтобы избежать явного дублирования большей части функций lambda ), хотя частично , конечно, осталось (это не полная дупликация и не бельмо на глазу).

Помните, что тело лямбда ограничено выражением , поэтому у него есть ограничения. Например ...:

>>> import functools
>>> f = functools.partial(int, base=2)
>>> f.args
()
>>> f.func
<type 'int'>
>>> f.keywords
{'base': 2}
>>> 

Возвращенная функция functools.partial украшена атрибутами, полезными для интроспекции - функцией, которую она оборачивает, и позиционными и именованными аргументами, которые она там исправляет. Кроме того, названные аргументы могут быть переопределены обратно («исправление» - это, скорее, в некотором смысле установка значений по умолчанию):

>>> f('23', base=10)
23

Итак, как вы видите, это определенно не такое упрощенное, как lambda s: int (s, base = 2) ! -)

Да, вы могли бы изменить свою лямбду, чтобы дать вам некоторые из них - например, для переопределения ключевого слова ,

>>> f = lambda s, **k: int(s, **dict({'base': 2}, **k))

но я очень надеюсь , что даже самый ярый лямбда -любитель не сочтет этот ужас более понятным, чем частичное ] вызов!-). Часть «установки атрибута» еще сложнее из-за ограничения Python лямбда «одним выражением тела» (плюс тот факт, что присваивание никогда не может быть частью выражения Python) ... вы в конечном итоге "подделка присваиваний в выражении" путем расширения понимания списка далеко за пределы его конструктивных ограничений ...:

>>> f = [f for f in (lambda f: int(s, base=2),)
           if setattr(f, 'keywords', {'base': 2}) is None][0]

Теперь объедините возможность переопределения именованных аргументов плюс установку трех атрибутов в одно выражение и расскажите мне, насколько удобочитаемым , что будет ...! -)

247
ответ дан 23 November 2019 в 06:00
поделиться

Я быстрее всего понял замысел в третьем примере.

Когда я разбираю лямбды, я ожидаю большей сложности/однозначности, чем предлагает непосредственно стандартная библиотека.

Кроме того, вы заметите, что третий пример - единственный, который не зависит от полной сигнатуры sum2; таким образом, он становится немного более свободно связанным.

1
ответ дан 23 November 2019 в 06:00
поделиться
Другие вопросы по тегам:

Похожие вопросы: