Использование карты python и других функциональных инструментов

Это довольно n00bish, но я пытаюсь изучить / понять функциональное программирование на python. Следующий код:

foos = [1.0,2.0,3.0,4.0,5.0] bars = [1,2,3] def maptest(foo, bar): print foo, bar map(maptest, foos, bars) 

производит:

 1.0 1 2.0 2 3.0 3 4.0 None 5.0 None 

В. Есть ли способ использовать карту или любые другие функциональные инструменты в python для создания следующих без циклов и т. Д.

 1.0 [1,2,3] 2.0 [1,2,3] 3.0 [1,2,3] 4.0 [1,2,3] 5.0 [1,2,3] 

Как примечание, как изменится реализация, если есть зависимость между foo и bar. например

 foos = [1.0,2.0,3.0,4.0,5.0] bars = [1,2,3,4,5] 

и печать:

 1.0 [2,3,4,5] 2.0 [1,3,4,5] 3.0 [1,2,4,5] ... 

PS: Я знаю, как это наивно использовать if, петли и / или генераторы, но я хотел бы узнать, как добиться того же, используя функциональные инструменты. Это всего лишь случай добавления инструкции if для maptest или применения другой карты фильтра к внутренним барам внутри maptest?

9 Solutions collect form web for “Использование карты python и других функциональных инструментов”

Самый простой способ – не пропускать bars через разные функции, а обращаться к нему непосредственно из maptest :

 foos = [1.0,2.0,3.0,4.0,5.0] bars = [1,2,3] def maptest(foo): print foo, bars map(maptest, foos) 

С вашей исходной функцией maptest вы также можете использовать лямбда-функцию на map :

 map((lambda foo: maptest(foo, bars)), foos) 

Вы знакомы с другими функциональными языками? т.е. пытаетесь ли вы узнать, как работает python для функционального программирования, или вы пытаетесь узнать о функциональном программировании и использовании python в качестве транспортного средства?

Кроме того, вы понимаете понимание списков?

 map(f, sequence) 

является прямым эквивалентом (*):

 [f(x) for x in sequence] 

На самом деле, я думаю, что map() был однажды намечен для удаления из python 3.0 как избыточный (этого не произошло).

 map(f, sequence1, sequence2) 

в основном эквивалентно:

 [f(x1, x2) for x1, x2 in zip(sequence1, sequence2)] 

(есть разница в том, как он обрабатывает случай, когда последовательности имеют разную длину.Как вы видели, map() заполняет None, когда одна из последовательностей заканчивается, тогда как zip() останавливается, когда заканчивается кратчайшая последовательность)

Итак, чтобы решить ваш конкретный вопрос, вы пытаетесь создать результат:

 foos[0], bars foos[1], bars foos[2], bars # etc. 

Вы можете сделать это, написав функцию, которая принимает один аргумент и печатает его, а затем строки:

 def maptest(x): print x, bars map(maptest, foos) 

Кроме того, вы можете создать список, который выглядит так:

 [bars, bars, bars, ] # etc. 

и используйте свой оригинальный maptest:

 def maptest(x, y): print x, y 

Одним из способов сделать это было бы прямое создание списка заранее:

 barses = [bars] * len(foos) map(maptest, foos, barses) 

Кроме того, вы можете itertools модуль itertools . itertools содержит множество умных функций, которые помогают вам выполнять программирование на ленивом уровне в стиле python. В этом случае мы хотим itertools.repeat , который будет выводить свой аргумент бесконечно, когда вы перебираете его. Этот последний факт означает, что если вы выполните:

 map(maptest, foos, itertools.repeat(bars)) 

вы получите бесконечный вывод, так как map() продолжает работать до тех пор, пока один из аргументов все еще производит вывод. Однако itertools.imap аналогичен map() , но останавливается, как только заканчивается кратчайший итерируемый.

 itertools.imap(maptest, foos, itertools.repeat(bars)) 

Надеюсь это поможет 🙂

(*) Это немного отличается в python 3.0. Там map () по существу возвращает выражение генератора.

Вот решение, которое вы ищете:

 >>> foos = [1.0, 2.0, 3.0, 4.0, 5.0] >>> bars = [1, 2, 3] >>> [(x, bars) for x in foos] [(1.0, [1, 2, 3]), (2.0, [1, 2, 3]), (3.0, [1, 2, 3]), (4.0, [1, 2, 3]), (5.0, [ 1, 2, 3])] 

Я бы рекомендовал использовать понимание списка (часть [(x, bars) for x in foos] ) с использованием карты, поскольку она позволяет избежать накладных расходов на вызов функции на каждой итерации (что может быть очень значительным). Если вы собираетесь использовать его в цикле for, вы получите более высокую скорость, используя понимание генератора:

 >>> y = ((x, bars) for x in foos) >>> for z in y: ... print z ... (1.0, [1, 2, 3]) (2.0, [1, 2, 3]) (3.0, [1, 2, 3]) (4.0, [1, 2, 3]) (5.0, [1, 2, 3]) 

Разница в том, что понимание генератора лениво загружается .

ОБНОВЛЕНИЕ В ответ на этот комментарий:

Конечно, вы знаете, что вы не копируете бары, все записи являются одним и тем же списком баров. Поэтому, если вы измените какой-либо из них (включая исходные бары), вы измените все из них.

Я полагаю, что это действительная точка. Есть два решения для этого, о которых я могу думать. Наиболее эффективным является, вероятно, что-то вроде этого:

 tbars = tuple(bars) [(x, tbars) for x in foos] 

Поскольку кортежи неизменяемы, это предотвратит изменение баров по результатам этого понимания списка (или понимание генератора, если вы идете по этому маршруту). Если вам действительно нужно изменить каждый из результатов, вы можете сделать это:

 from copy import copy [(x, copy(bars)) for x in foos] 

Однако это может быть немного дорогим как с точки зрения использования памяти, так и с точки зрения скорости, поэтому я бы рекомендовал против нее, если вам действительно не нужно добавлять к каждому из них.

Функциональное программирование – это создание кода без побочных эффектов.

map – абстракция преобразования функционального списка. Вы используете его, чтобы принять последовательность чего-то и превратить его в последовательность чего-то другого.

Вы пытаетесь использовать его как итератор. Не делай этого. 🙂

Вот пример того, как вы можете использовать карту для создания нужного вам списка. Есть более короткие решения (я бы просто использовал понимание), но это поможет вам понять, какая карта немного лучше:

 def my_transform_function(input): return [input, [1, 2, 3]] new_list = map(my_transform, input_list) 

Обратите внимание, что вы только сделали манипуляции с данными. Теперь вы можете распечатать его:

 for n,l in new_list: print n, ll 

– Я не уверен, что вы подразумеваете под «без петель». fp не об избегании циклов (вы не можете просматривать каждый элемент в списке, не посещая их). Речь идет об избегании побочных эффектов, тем самым создавая меньше ошибок.

 >>> from itertools import repeat >>> for foo, bars in zip(foos, repeat(bars)): ... print foo, bars ... 1.0 [1, 2, 3] 2.0 [1, 2, 3] 3.0 [1, 2, 3] 4.0 [1, 2, 3] 5.0 [1, 2, 3] 
 import itertools foos=[1.0, 2.0, 3.0, 4.0, 5.0] bars=[1, 2, 3] print zip(foos, itertools.cycle([bars])) 

Ниже приведен обзор параметров функции map(function, *sequences) :

  • function – это имя вашей функции.
  • sequences – это любое количество последовательностей, которые обычно являются списками или кортежами. map будет перебирать их одновременно и давать текущие значения function . Вот почему количество последовательностей должно соответствовать количеству параметров вашей функции.

Похоже, вы пытаетесь выполнить итерацию некоторых параметров функции, но сохраняете другие постоянными, и, к сожалению, map не поддерживает это. Я нашел старое предложение добавить такую ​​функцию к Python, но конструкция карты настолько чиста и устоялась, что я сомневаюсь, что что-то подобное будет реализовано.

Используйте обходной путь, например глобальные переменные или списки, как это предлагали другие.

Будет ли это делать?

 foos = [1.0,2.0,3.0,4.0,5.0] bars = [1,2,3] def maptest2(bar): print bar def maptest(foo): print foo map(maptest2, bars) map(maptest, foos) 

Как насчет этого:

 foos = [1.0,2.0,3.0,4.0,5.0] bars = [1,2,3] def maptest(foo, bar): print foo, bar map(maptest, foos, [bars]*len(foos)) 
 
Interesting Posts for Van-Lav

Как ` :: OutputEncoding / InputEncoding` с Python?

Преобразование столбцов времени в минутах в формате времени в формате HH: MM: SS в пандах

Что делает этот кусок кода Python?

Экспоненциальное отключение: time.sleep с random.randint (0, 1000) / 1000

Как использовать scikit-learn PCA для уменьшения возможностей и знать, какие функции отбрасываются

Scikit-Learn Классификация и регрессия с весами

Как интерпретировать вывод TensorFlow?

Как создать пустой массив / матрицу в NumPy?

Как я могу исправить и оптимизировать этот очень простой фрагмент кода «Игры жизни», используя функциональность NumPy?

Классифицируйте файлы csv на основе информации за 18 долларов и найдите файл csv в каждой категории с самым большим уникальным номером в $ 4

Извлечение токена и секрет из объекта gdata.gauth.OAuthHmacToken python

В Python, как распечатать сообщение об ошибке без печати трассировки и закрыть программу, когда условие не выполняется?

Как исправить ошибки PyDev «Неопределенная переменная из импорта»?

Очередь задач работает с представлением, но UnknownQueueError при запуске от модульных тестов

Мое первое веб-приложение (Python): используйте CGI или фреймворк вроде Django?

Python - лучший язык программирования в мире.