Когда я анализирую исходный код с ast
модулем, почему это lineno
атрибута Name
внутри FormattedValue
установлены в 1, даже когда диафрагменная строке не на линии 1?Номер строк из Python F-строк в абстрактном синтаксическом дереве
Я пытаюсь увидеть, какие строки исходного кода включены в определение функции, поэтому я иду узлами абстрактного синтаксического дерева ниже узла FunctionDef
. Я собираю все атрибуты lineno
в набор, и это говорит мне, какие строки являются частью определения функции.
Однако, когда в Python 3.6 появился f-strings, они каким-то образом нарушили эту технику. Вот пример задачи:
import ast
code = """\
f'x{y}'
"""
tree = ast.parse(code)
print(ast.dump(tree, include_attributes=True))
Вот выход из этого сценария:
Module(body=[Expr(value=JoinedStr(values=[Str(s='x', lineno=2, col_offset=0), FormattedValue(value=Name(id='y', ctx=Load(), lineno=1, col_offset=1), conversion=-1, format_spec=None, lineno=2, col_offset=0)], lineno=2, col_offset=0), lineno=2, col_offset=0)])
Я знаю, что это довольно нечитаемыми, так что здесь тот же результат, с некоторыми дополнительными пробелами:
Module(body=[Expr(value=JoinedStr(values=[
Str(s='x', lineno=2, col_offset=0),
FormattedValue(value=Name(id='y',
ctx=Load(),
lineno=1,
col_offset=1),
conversion=-1,
format_spec=None,
lineno=2,
col_offset=0)], lineno=2, col_offset=0), lineno=2, col_offset=0)])
Единственный исходный код был в строке 2, так что же с этой частью вывода?
Name(id='y',
ctx=Load(),
lineno=1,
col_offset=1)
Я думал, что это может быть номер строки в строка, но когда я пытаюсь это, она по-прежнему сообщает lineno=1
.
code = """\
f'''
x{y}'''
"""