2013-04-15 3 views
38

Есть ли ссылка где-то точно определяющая, когда вложение кортежей с круглыми скобками является или не требуется?Когда требуются круглые скобки вокруг кортежа?

Вот пример того, что меня удивило в последнее время:

>>> d = {} 
>>> d[0,] = 'potato' 
>>> if 0, in d: 
    File "<stdin>", line 1 
    if 0, in d: 
     ^
SyntaxError: invalid syntax 
+4

Я нахожу это особенно интересно, что 'для k, in d: печать k' действительно работа в этом случае. –

+0

[Python grammar] (http://docs.python.org/2/reference/grammar.html) покажет вам, что * * разрешено, например, в инструкции 'if'.Вам нужно будет прочитать полную грамматику, чтобы понять, где приняты неравноценные кортежи, поэтому я не отправляю это как ответ. – chepner

+0

... Я не понимаю, как вы могли быть удивлены * с ошибкой 'for' с' 0, '... идентификаторы python должны начинаться с буквы (unicode) или подчеркивания, а' 0' недействительны поэтому я бы ожидал * a «SyntaxError». – Bakuriu

ответ

38

Объединение выражений для создания кортежа с помощью маркера запятой называется в expression_list. Правила operator precedence не охватывают списки выражений; это потому, что списки выражений сами по себе не являются выражениями; они становятся выражениями, заключенными в круглые скобки.

это так, неохваченная expression_list допускается в любом месте в Python, что это специально разрешено грамматикой языка, но не где expression как таковой требуется.

Например, грамматика if statement выглядит следующим образом:

if_stmt ::= "if" expression ":" suite 
      ("elif" expression ":" suite)* 
      ["else" ":" suite] 

Поскольку производство expression ссылаются, неохваченная expression_list s не допускаются в качестве субъекта if заявления. Однако for statement принимает expression_list:

for_stmt ::= "for" target_list "in" expression_list ":" suite 
       ["else" ":" suite] 

Так следующее разрешено:

for x in 1, 2, 3: 
    print(x) 
+2

+1 Это, безусловно, объясняет, почему' для k, в d' works (потому что 'for k, v in d' works). –

+0

Вопрос: Должны ли вы писать его 'для x в 1, 2, 3:' или 'для x в (1, 2, 3):'? Я всегда писал это вторым способом, но это было потому, что я не знал, что первый способ действителен до тех пор, пока я не попробовал. Теперь мне интересно, являются ли '()' ненужным шумом или если они каким-то образом помогают в чтении кода. Предоставляет ли PEP8 какие-либо рекомендации по этому вопросу? – ArtOfWarfare

+1

@ArtOfWarfare нет никаких конкретных указаний в PEP8. Это может помочь сравнить с операторами 'if', где скобки рекомендуются только для условия, которое охватывает несколько строк. Итак: 'для x in (1, 2, 3):'. – ecatmur

11

Везде, где разрешено использовать expression_list термин, вам не нужно использовать круглые скобки.

if statement требует expression и не поддерживает expression_list.

Примеры синтаксиса, который действительно позволяет expression_list:

документации оглавлению Expressions, Simple и Compound statements для expression_list покажет вам все места, которые expression_list используется в грамматике Python.

+0

О да? Как насчет '1,2,3 + 4,5'? Это не приводит к списку выражений, который вы могли бы ожидать ... – smci

+0

@smci, что связано с моим ответом? Какой результат вы ожидали? –

+0

Потому что '1,2,3 + 4,5' приводит к выражению' 1,2,7,5', чего не ожидает случайный читатель, и происходит от перегрузки '+' для добавления последовательности. – smci

1

Скобки также необходимы, если вы хотите , чтобы избежать двусмысленности.

Ниже приведены два различных выражения ... только потому, что что-то есть «список выражений», не приводит в списке выражений можно было бы ожидать :)

(1, 2, 3) + (4, 5) # results in (1, 2, 3, 4, 5) because + does sequence.extend on the tuples 
1, 2, 3 + 4, 5  # this results in (1, 2, 7, 5) because + adds the elements, since there were no parentheses to protect the separate tuples 
Смежные вопросы