Python PLY 解析:定义范围
Python PLY parsing : definition scope
我正在使用 PLY 来解析包含嵌套块的文件。
通常:
a {
b {
}
c {
d {
}
}
}
我正在使用像这样的简单语法:
def p_nodes(p):
'''
nodes : node nodes
| node
'''
# ??
def p_node(p):
'''
node : IDENTIFIER OPEN_CURLY_BRACE node_çontent CLOSE_CURLY_BRACE
'''
p[0] = Node(p[3])#FIXME?
def p_node_content(p):
'''
node_content : nodes
|
'''
if len(p) > 1:
p[0] = p[1]
else
p[0] = None
我想知道我可以访问解析器中的 'parent' 节点。换句话说,我如何构建 AST 以便我可以在我的示例中检索 d
是 c
的子级,它本身是 a
的子级,因为我必须对父规则可见在解析器中。
我应该在 p_nodes
和 p_node
中输入什么才能构建有效的 AST?谢谢。
我们需要您的 Node
class,但我认为它类似于:
class Node:
def __init__(self, children):
self.children = children
self.type = None
那么你的解析器可能看起来像这样:
def p_nodes(p):
'''
nodes : node nodes
| node
'''
if len(p) > 2:
p[0] = [p[1]] + p[2]
else
p[0] = [p[1]]
def p_node(p):
'''
node : IDENTIFIER OPEN_CURLY_BRACE node_content CLOSE_CURLY_BRACE
'''
p[0] = Node(p[3])
def p_node_content(p):
'''
node_content : nodes
|
'''
if len(p) > 1:
p[0] = p[1]
else
p[0] = None
那么你将拥有一个真正的 AST,每个节点都包含对其所有子节点的引用。
最后,如果你想让你的节点引用它们的父节点,你必须从根开始迭代所有的 AST,并将它设置为他所有子节点的属性,然后对它的子节点做同样的事情。 ..
为此,请将您的 Node
class 更改为如下所示:
class Node:
def __init__(self, children):
self.children = children
self.parent = None
def set_parent(self, parent):
self.parent = parent
和运行类似的函数:
def set_parent_to_AST(root_node):
for node in root_node.children:
node.set_parent(root_node)
set_parent_to_AST(node)
我正在使用 PLY 来解析包含嵌套块的文件。 通常:
a {
b {
}
c {
d {
}
}
}
我正在使用像这样的简单语法:
def p_nodes(p):
'''
nodes : node nodes
| node
'''
# ??
def p_node(p):
'''
node : IDENTIFIER OPEN_CURLY_BRACE node_çontent CLOSE_CURLY_BRACE
'''
p[0] = Node(p[3])#FIXME?
def p_node_content(p):
'''
node_content : nodes
|
'''
if len(p) > 1:
p[0] = p[1]
else
p[0] = None
我想知道我可以访问解析器中的 'parent' 节点。换句话说,我如何构建 AST 以便我可以在我的示例中检索 d
是 c
的子级,它本身是 a
的子级,因为我必须对父规则可见在解析器中。
我应该在 p_nodes
和 p_node
中输入什么才能构建有效的 AST?谢谢。
我们需要您的 Node
class,但我认为它类似于:
class Node:
def __init__(self, children):
self.children = children
self.type = None
那么你的解析器可能看起来像这样:
def p_nodes(p):
'''
nodes : node nodes
| node
'''
if len(p) > 2:
p[0] = [p[1]] + p[2]
else
p[0] = [p[1]]
def p_node(p):
'''
node : IDENTIFIER OPEN_CURLY_BRACE node_content CLOSE_CURLY_BRACE
'''
p[0] = Node(p[3])
def p_node_content(p):
'''
node_content : nodes
|
'''
if len(p) > 1:
p[0] = p[1]
else
p[0] = None
那么你将拥有一个真正的 AST,每个节点都包含对其所有子节点的引用。
最后,如果你想让你的节点引用它们的父节点,你必须从根开始迭代所有的 AST,并将它设置为他所有子节点的属性,然后对它的子节点做同样的事情。 ..
为此,请将您的 Node
class 更改为如下所示:
class Node:
def __init__(self, children):
self.children = children
self.parent = None
def set_parent(self, parent):
self.parent = parent
和运行类似的函数:
def set_parent_to_AST(root_node):
for node in root_node.children:
node.set_parent(root_node)
set_parent_to_AST(node)