[Python] объясните выражение
От: victor_kr Украина  
Дата: 15.07.10 09:49
Оценка:
В документации встретил выражение. Вот его упрощенный работающий вариант:

print ', '.join(i for i in ['1', '2'])


Не могу понять что означает i перед for. join принимает итератор. Значит то что написано в скобках после join должно возвращать итератор. При попытке присвоить это "i for i in ['1', '2']" выражение переменной возникает ошибка. Хотя, если я пробую присвоить переменной "[i for i in ['1', '2']]" или "(i for i in ['1', '2'])", то получаю в переменной итератор. Хотя эта запись мне не понятна тоже.

Получается, что в выражении не хватает скобок. Нужно писать так:

print ', '.join([i for i in ['1', '2']])


Укажите пожалуйста место в докуметации, где описывается подобный синтаксис. Интересует именно i for i in ['1', '2'].
Re: [Python] объясните выражение
От: Мишень-сан  
Дата: 15.07.10 09:57
Оценка: +1 -1
Здравствуйте, victor_kr, Вы писали:

_>Укажите пожалуйста место в докуметации, где описывается подобный синтаксис. Интересует именно i for i in ['1', '2'].


Тыц

Ещё есть Generator comprehension (i for i in ['1', '2']) и Dictionary Comprehension {i : i**2 for i in ['1', '2']}
Соответственно, List comp. создаёт список, Gen comp. создаёт генератор (условно-ленивая последовательность), а Dictionary comp. создаёт словарь
Re[2]: [Python] объясните выражение
От: Мишень-сан  
Дата: 15.07.10 09:59
Оценка:
Здравствуйте, Мишень-сан, Вы писали:

МС>Здравствуйте, victor_kr, Вы писали:


_>>Укажите пожалуйста место в докуметации, где описывается подобный синтаксис. Интересует именно i for i in ['1', '2'].


МС>Тыц


МС>Ещё есть Generator comprehension (i for i in ['1', '2']) и Dictionary Comprehension {i : i**2 for i in ['1', '2']}

МС>Соответственно, List comp. создаёт список, Gen comp. создаёт генератор (условно-ленивая последовательность), а Dictionary comp. создаёт словарь

UPD: скорее всего, первое выражение в Вашем посте создало как раз генератор
Re: [Python] объясните выражение
От: Temoto  
Дата: 15.07.10 10:18
Оценка: 1 (1) +1
_>В документации встретил выражение. Вот его упрощенный работающий вариант:

_>
_>print ', '.join(i for i in ['1', '2'])
_>


_>Не могу понять что означает i перед for. join принимает итератор. Значит то что написано в скобках после join должно возвращать итератор. При попытке присвоить это "i for i in ['1', '2']" выражение переменной возникает ошибка. Хотя, если я пробую присвоить переменной "[i for i in ['1', '2']]" или "(i for i in ['1', '2'])", то получаю в переменной итератор. Хотя эта запись мне не понятна тоже.


_>Получается, что в выражении не хватает скобок. Нужно писать так:


_>
_>print ', '.join([i for i in ['1', '2']])
_>


Можно, но не нужно. Если б там нехватало скобок, эта строка бы не работала. А вы добавили лишних скобок (и изменили смысл выражения).

_>Укажите пожалуйста место в докуметации, где описывается подобный синтаксис. Интересует именно i for i in ['1', '2'].


В данном случае имеем generator comprehension, который, будучи единственным аргументом к функции может быть записан без скобок. То есть без изменения смысла это выражение пишется так: ', '.join((i for i in ['1', '2'])). Двойные скобки никому не нужны, их можно опустить.

Что за i перед for лучше, конечно вдумчиво прочитать по ссылке http://docs.python.org/release/2.6.5/tutorial/datastructures.html#list-comprehensions Но, для ленивых, вкратце суть вот в чём: ( expr for bind in iterable ) делает примерно следущее:

for bind in iterable:
yield expr

соответственно, генератор компрехеншон честно создаёт генератор (ленивый список), а лист компрехеншон создаёт строгий список, вычисляет все элементы сразу.
Re[3]: [Python] объясните выражение
От: victor_kr Украина  
Дата: 15.07.10 10:24
Оценка:
За ссылку спасибо. Посмотрите:


>>> type((i for i in ['1', '2'])) # внутренние круглые скобки "говорят" что это герератор
<type 'generator'>
>>> type([i for i in ['1', '2']]) # квадратные скобки "говорят" что это список
<type 'list'>
>>> type(i for i in ['1', '2']) # есть только одни круглые скобки, которые относятся к функции type, предполагаю, что то что в этих скобках можно присвоить переменной 
<type 'generator'>
>>> gen = i for i in ['1', '2'] # но получаю ошибку, получается не хватает скобок? почему работает при вызове функции?
SyntaxError: invalid syntax
>>> gen = (i for i in ['1', '2']) # генератор
>>> type(gen)
<type 'generator'>
>>> gen = [i for i in ['1', '2']] # список
>>> type(gen)
<type 'list'>


В разделе 5.1.4 есть пример вызова функции:


print([[row[i] for row in mat] for i in [0, 1, 2]])


Есть квадратные скобки. Получается недокументированная возможность?
Re: [Python] объясните выражение
От: victor_kr Украина  
Дата: 15.07.10 10:43
Оценка:
Насчет лишних скобок, которые никому не нужны. Зачем тогда писать скобки при вызове метода, который не принимает параметров?
Re[2]: [Python] объясните выражение
От: Temoto  
Дата: 15.07.10 11:49
Оценка:
_>Насчет лишних скобок, которые никому не нужны. Зачем тогда писать скобки при вызове метода, который не принимает параметров?

Без скобок было бы непонятно — вы хотите вызвать эту функцию или передать ещё как параметр, без вызова.

def foo():
  return "ok"


В питоне str(foo) вернёт строковое представление *функции*, то есть '<function foo at 0x123123123>'. А str(foo()) вызовет функцию и вернёт 'ok'. Иногда нужно одно, иногда другое.


В Ruby вот синтаксис позволяет вызывать без скобок (что есть большой плюс, меньше синтаксического мусора). Минус в том, что функцию нельзя передать параметром.
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.