Есть ли у кого-нибудь здесь полезный код, который использует функцию reduce () в python? Есть ли какой-либо другой код, кроме обычных + и *, который мы видим в примерах?
Обратитесь к Fate of reduce () в Python 3000 от GvR
Есть ли у кого-нибудь здесь полезный код, который использует функцию reduce () в python? Есть ли какой-либо другой код, кроме обычных + и *, который мы видим в примерах?
Обратитесь к Fate of reduce () в Python 3000 от GvR
from functools import reduce
позволяет одному и тому же коду работать как на Python 2, так и на Python 3.Ответы:
Другие применения, которые я нашел для него, помимо + и *, были с и и или, но теперь у нас есть
any
иall
для замены этих случаев.foldl
иfoldr
действительно часто появляются в схеме ...Вот несколько милых приемов:
Свести список
Цель: превратиться
[[1, 2, 3], [4, 5], [6, 7, 8]]
в[1, 2, 3, 4, 5, 6, 7, 8]
.Список цифр в число
Цель: превратиться
[1, 2, 3, 4, 5, 6, 7, 8]
в12345678
.Уродливый, медленный путь:
Красиво
reduce
:источник
timeit.repeat('int("".join(map(str, digit_list)))', setup = 'digit_list = list(d%10 for d in xrange(1,1000))', number=1000)
занимает ~ 0,09 секунды, аtimeit.repeat('reduce(lambda a,d: 10*a+d, digit_list)', setup = 'digit_list = list(d%10 for d in xrange(1,1000))', number=1000)
занимает 0,36 секунды (примерно в 4 раза медленнее). Обычно умножение на 10 становится дорогим, когда список становится большим, в то время как int в str и конкатенация остаются дешевыми.timeit.repeat('convert_digit_list_to_int(digit_list)', setup = 'digit_list = [d%10 for d in xrange(1,10)]\ndef convert_digit_list_to_int(digits):\n i = 0\n for d in digits:\n i = 10*i + d\n return i', number=100000)
занимает 0,06 с,timeit.repeat('reduce(lambda a,d: 10*a+d, digit_list)', setup = 'digit_list = list(d%10 for d in xrange(1,10))', number=100000)
занимает 0,12 с, а преобразование цифр в метод str занимает 0,16 с.reduce()
можно использовать для поиска наименьшего общего кратного для 3 или более чисел :Пример:
источник
lcm
во второй строке?lcm()
возвращает наименьшее общее кратное двух чисел.reduce()
может использоваться для разрешения имен, разделенных точками (гдеeval()
это слишком небезопасно для использования):источник
Найдите пересечение N заданных списков:
возвращает:
через: Python - пересечение двух списков
источник
Я думаю, что сокращение - глупая команда. Следовательно:
источник
Использование того,
reduce
что я нашел в своем коде, связано с ситуацией, когда у меня была некоторая структура классов для логического выражения, и мне нужно было преобразовать список этих объектов выражения в соединение выражений. У меня уже была функцияmake_and
для создания конъюнкции по двум выражениям, поэтому я написалreduce(make_and,l)
. (Я знал, что список не пустой, иначе было бы что-то вродеreduce(make_and,l,make_true)
.)Именно по этой причине (некоторым) функциональным программистам нравятся
reduce
(или складываются функции, как обычно их называют). Есть часто уже много бинарных функций , таких как+
,*
,min
,max
, конкатенация и, в моем случае,make_and
иmake_or
. Наличие areduce
делает тривиальным преобразование этих операций в списки (или деревья, или что-то еще, для функций сворачивания в целом).Конечно, если
sum
часто используются определенные экземпляры (например, ), то вы не хотите продолжать писатьreduce
. Однако вместо того, чтобы определять сsum
помощью некоторого цикла for, вы можете так же легко определить его с помощьюreduce
.Читаемость, как упоминалось другими, действительно проблема. Однако вы можете возразить, что единственная причина, по которой люди находят
reduce
менее «ясным», заключается в том, что это не функция, которую многие люди знают и / или используют.источник
and
оператора:L and reduce(make_and, L)
если в этом случае уместен возврат пустого спискаСостав функций : если у вас уже есть список функций, которые вы хотите применить последовательно, например:
Затем вы можете применить их все последовательно с помощью:
В этом случае цепочка методов может быть более читаемой. Но иногда это невозможно, и такая композиция может быть более читаемой и удобной, чем какой-
f1(f2(f3(f4(x))))
то синтаксис.источник
Вы можете заменить
value = json_obj['a']['b']['c']['d']['e']
на:Если у вас уже есть путь
a/b/c/..
в виде списка. Например, изменить значения в словах вложенных слов, используя элементы в списке .источник
@Blair Conrad: Вы также можете реализовать свой glob / reduce, используя сумму, например:
Это менее подробный, чем любой из ваших двух примеров, идеально подходит для Python и по-прежнему представляет собой всего одну строку кода.
Итак, чтобы ответить на исходный вопрос, я лично стараюсь избегать использования reduce, потому что в этом нет необходимости, и я считаю, что это менее понятно, чем другие подходы. Однако некоторые люди привыкли сокращать и предпочитают перечислять понимания (особенно программисты на Haskell). Но если вы еще не думаете о проблеме с точки зрения сокращения, вам, вероятно, не нужно беспокоиться об ее использовании.
источник
sum
иreduce
приводят к квадратичному поведению. Это может быть сделано в линейное время:files = chain.from_iterable(imap(iglob, args))
. Хотя в данном случае это, вероятно, не имеет значения из-за времени, которое требуется glob () для доступа к диску.reduce
может использоваться для поддержки поиска связанных атрибутов:Конечно, это эквивалентно
но это полезно, когда ваш код должен принимать произвольный список атрибутов.
(Связанные атрибуты произвольной длины распространены при работе с моделями Django.)
источник
reduce
полезен, когда вам нужно найти объединение или пересечение последовательностиset
-подобных объектов.(Помимо фактических
set
s, примером этого являются объекты Q Django .)С другой стороны, если вы имеете дело с
bool
s, вам следует использоватьany
andall
:источник
После greping моего кода кажется, что единственное, что я использовал для сокращения, - это вычисление факториала:
источник
Я пишу функцию составления для языка, поэтому я создаю составную функцию, используя сокращение вместе с оператором применения.
Вкратце, compose принимает список функций, которые нужно объединить в одну функцию. Если у меня есть сложная операция, которая выполняется поэтапно, я хочу собрать все это так:
Таким образом, я могу применить его к такому выражению:
И я хочу, чтобы это было эквивалентно:
Теперь, чтобы построить свои внутренние объекты, я хочу, чтобы он сказал:
(Класс Lambda создает пользовательскую функцию, а Apply создает приложение-функцию.)
Теперь уменьшите, к сожалению, неправильные складки, поэтому я примерно использовал:
Чтобы выяснить, что дает сокращение, попробуйте следующее в REPL:
источник
compose = lambda *func: lambda arg: reduce(lambda x, f: f(x), reversed(funcs), arg)
чтобы сгенерировать все возможные комбинации функций для тестирования производительности.reduce можно использовать для получения списка с максимальным n-м элементом
вернет [5, 2, 5, 7], поскольку это список с максимальным 3-м элементом +
источник
Reduce не ограничивается скалярными операциями; его также можно использовать для сортировки вещей по ведрам. (Это то, что я использую чаще всего).
Представьте себе случай, когда у вас есть список объектов, и вы хотите реорганизовать его иерархически на основе свойств, хранящихся в объекте. В следующем примере я создаю список объектов метаданных, связанных со статьями в XML-закодированной газете с помощью
articles
функции.articles
генерирует список элементов XML, а затем отображает их один за другим, создавая объекты, содержащие некоторую интересную информацию о них. Во внешнем интерфейсе я хочу, чтобы пользователь мог просматривать статьи по разделам / подразделам / заголовкам. Поэтому я использую,reduce
чтобы взять список статей и вернуть единственный словарь, который отражает иерархию разделов / подразделов / статей.Я привожу здесь обе функции, потому что считаю, что это показывает, как map и reduce могут хорошо дополнять друг друга при работе с объектами. То же самое можно было бы сделать с помощью цикла for, ... но серьезное времяпровождение с функциональным языком заставляло меня думать в терминах map и reduce.
Между прочим, если у кого-нибудь есть лучший способ установить свойства, как это делаю я
extract
, где родители свойства, которое вы хотите установить, могут еще не существовать, сообщите мне.источник
Не уверен, что это то, что вам нужно, но вы можете поискать исходный код в Google .
Перейдите по ссылке для поиска по запросу 'function: reduce () lang: python' в поиске Google Code.
На первый взгляд следующие проекты используют
reduce()
и т.д. и т.п., но в этом нет ничего удивительного, поскольку это огромные проекты.
Функциональность сокращения может быть реализована с помощью рекурсии функций, что, как мне кажется, Гвидо считал более явным.
Обновить:
Так как поиск кода Google был прекращен 15 января 2012 года, помимо возврата к обычному поиску в Google, есть нечто под названием Code Snippets Collection, которое выглядит многообещающим. В ответах на этот (закрытый) вопрос упоминается ряд других ресурсов. Замена для Google Code Search? ,
Обновление 2 (29 мая 2017 г.):
Хорошим источником примеров Python (с открытым исходным кодом) является поисковая система Nullege .
источник
for
цикла.lang:python "reduce("
найдет определения вreduce
зависимости от стиля кодирования исходного кода.источник
источник
Я использовал
reduce
для объединения список векторов поиска PostgreSQL с||
оператором в sqlalchemy-searchchable:источник
У меня есть старая реализация pipegrep на Python, которая использует модуль reduce и glob для создания списка файлов для обработки:
Тогда мне это показалось удобным, но на самом деле в этом нет необходимости, поскольку что-то подобное так же хорошо и, вероятно, более читабельно.
источник
files = [glob.glob(f) for f in args]
itertools
, используяflatten()
рецепт из docs.python.org/library/itertools.html , а затем написать:files = flatten(glob.glob(f) for f in args)
(И на этот раз я протестировал код перед его публикацией, и я знаю, что это работает правильно.)files = chain.from_iterable(imap(iglob, args))
гдеchain
,imap
относятся кitertools
модулю иglob.iglob
полезны, если по шаблону изargs
могут быть получены файлы из нескольких каталогов.Допустим, есть некоторые годовые статистические данные, хранящиеся в списке счетчиков. Мы хотим найти значения MIN / MAX для каждого месяца в разные годы. Например, для января это будет 10. А для февраля - 15. Нам нужно сохранить результаты в новом счетчике.
источник
У меня есть объекты, представляющие своего рода перекрывающиеся интервалы (геномные экзоны), и я переопределил их пересечение, используя
__and__
:Затем, когда у меня есть их коллекция (например, в том же гене), я использую
источник
Я только что нашел полезное использование
reduce
: разделение строки без удаления разделителя . Код полностью взят из блога Programatic Speaking. Вот код:Вот результат:
Обратите внимание, что он обрабатывает крайние случаи, которых не делает популярный ответ в SO. Для более подробного объяснения я перенаправляю вас к исходному сообщению в блоге.
источник
Использование reduce (), чтобы узнать, являются ли даты последовательными:
источник