2015-12-09 5 views
1

Я могу создать строку из нескольких строк, используя следующий синтаксис:Python строкового литерала конкатенация

string = str("Some chars " 
     "Some more chars") 

Это будет производить следующую строку:

"Some chars Some more chars" 

Является Python, соединяющий эти две отдельных строк или является редактор/компилятор обрабатывает их как одну строку?

P.s: Я просто хочу понять внутренности. Я знаю, что есть другие способы объявить или создать многострочные строки.

+2

«Включает ли python эти две отдельные строки» - да, это так. [Это поведение даже документировано.] (Https://docs.python.org/2/reference/lexical_analysis.html#string-literal-concatenation) – vaultah

+0

Это не ** многострочная строка **. Эта функция не имеет ничего общего с разрывами строк. Python игнорирует разрыв строки из-за скобки. BTW, многострочная строка может быть создана с использованием тройных кавычек ('' "" 'или' '' ''). – zvone

ответ

12

Прочитано reference manual, Это там. частности:

несколько смежной строки или байт литералы (с разделителями пробелами), возможно, с использованием различного цитирования конвенции, разрешаются, и их значение такого же, как их конкатенация. Таким образом, «привет» «мир» эквивалентен «helloworld». Эта функция может быть использована для уменьшения количества обратных косых черт, необходимых, для разделения длинных строк удобно через длинные линии, или даже добавлять комментарии к частям строк,

(курсив мой)

Вот почему:

string = str("Some chars " 
     "Some more chars") 

точно так же, как: str("Some chars Some more chars").

Это действие выполняется везде, где может отображаться строковый литерал, перечислять инициализации, вызовы функций (как в случае с str выше) и т. Д.

Единственное предостережение, когда строковый не заключенных между одним из grouping delimiters(), {} or [], но, вместо этого, спредов между двумя отдельными physical lines. В этом случае мы можем в качестве альтернативы use обратной косой черты, чтобы соединить эти строки и получить тот же результат:

string = "Some chars " \ 
     "Some more chars" 

Конечно, конкатенация строк на одной и той же физической линии не требует обратной косой черты. (string = "Hello " "World" просто отлично)


Является Python, соединяющий эти две отдельных строк или редактор/компилятор рассматривать их как одну строку?

Питон, теперь когда именно делает Python делать это становится все интереснее.

Из того, что я мог собрать (принять это с щепоткой соли, я не эксперт в разборе), это происходит, когда Python трансформирует дерево синтаксического анализа (LL(1) Parser) для данного выражения это соответствующее AST (Abstract Syntax Tree).

Вы можете получить вид на обработанном дереве через parser модуля:

import parser 

expr = """ 
     str("Hello " 
      "World") 
""" 
pexpr = parser.expr(expr) 
parser.st2list(pexpr) 

Это отвалы довольно большой и запутанный список, который представляет конкретное дерево синтаксиса проанализированного из выражения в expr:

-- rest snipped for brevity -- 

      [322, 
      [323, 
       [3, '"hello"'], 
       [3, '"world"']]]]]]]]]]]]]]]]]], 

-- rest snipped for brevity -- 

Цифры соответствуют либо символам, либо маркерам в дереве разбора, а отображения из символа в правило грамматики и токена в константу находятся в Lib/symbol.py и Lib/token.py соответственно.

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

Далее мы можем увидеть выход AST дерева, полученного в предыдущем выражении через модуль ast, представленный в стандартной библиотеке:

p = ast.parse(expr) 
ast.dump(p) 

# this prints out the following: 
"Module(body = [Expr(value = Call(func = Name(id = 'str', ctx = Load()), args = [Str(s = 'hello world')], keywords = []))])" 

Выходом является более дружественным к пользователю в данном случае; вы можете видеть, что args для вызова функции является единственной конкатенированной строкой Hello World.

Кроме того, я также наткнулся на классный module, который генерирует визуализацию дерева для узлов ast. С его помощью, выход экспрессии expr визуализируется как это:

                                                                                      expression tree for the given expression

Изображение обрезается, чтобы показать только соответствующую часть для выражения.

Как вы можете видеть, в узле терминала листа у нас есть один str объекта, соединенная строка для "Hello " и "World", я.e "Hello World".


Если вы чувствуете себя достаточно храбр, копаться в источнике, исходный код для преобразования выражения в синтаксическое дерево находится в Parser/pgen.c в то время как код преобразования дерева синтаксического разбора в абстрактное синтаксическое дерево в Python/ast.c.

Эта информация для Python 3.5, и я уверен, что если вы не используете какой-то действительно старую версию (< 2.5) функциональность и местоположения должны быть похожими.

Кроме того, если вы заинтересованы во всем этапе компиляции питона следует, хороший нежный интро обеспечиваются одним из основных доноров, Бретт Cannon, в видео From Source to Code: How CPython's Compiler Works.

+0

Спасибо за ваш ответ, который очищает мои сомнения. Кроме того, я хотел бы спросить, когда я говорю« Некоторые символы »и на следующей строке я говорю «Еще несколько символов», не заключая в скобки, он не будет выдавать одинаковый результат. Итак, когда они говорят пробелы, они не означают новые строки, не так ли? –

+0

Вы можете опустить 'str' – falsetru

+0

@falsetru без скобок это не сработает.Это просто заполнитель, чтобы удовлетворить python :) –