簡體   English   中英

在Python2.7 ANTLR4中,從解析器規則中提取令牌並將其存儲在列表中

[英]In Python2.7 ANTLR4, extract tokens from a parser rule and store them in a list

在我的語法中,我驗證看起來像這樣的布爾表達式:

((foo == true) && (bar != false) || (qux == norf))

我通過調用getText()從ANTLR4的上下文對象獲取字符串:

def enterBody(self, ctx):
    expression = ctx.condition.getText() # condition here being shorthand for a grammar rule (`condition=expr`)

但是,該字符串全部返回(即,每個標記之間沒有空格),並且我無法知道每個標記是什么:

((foo==true)&&(bar!=false)||(qux==norf))

理想情況下,我希望它以以下格式存儲在列表中:

['(', '(', 'foo', '==', 'true', ')', '&&', '(', 'bar', '!=', 'false', ')', '||', '(', 'qux', '==', 'norf', ')', ')']

ANTLR4 Python文檔非常稀疏,我不確定是否有實現此目的的方法。

Python運行時確實類似於Java運行時,因此您可以查看Java文檔,並且很可能在Python中存在相同的方法。 或瀏覽源代碼 ,這很容易閱讀。

您要獲取平面字符串列表。 但是解析器的整個想法是避免這種情況。 因此,我認為這很可能不是您需要的東西。 確保了解解析樹以及偵聽器的工作方式 基本上,您應該使用樹而不是平面列表。 您可能正在尋找的是ParserRuleContext.getChildren() 您可以使用它來訪問所有子節點:

def enterBody(self, ctx):
    print(list(ctx.getChildren()))

您甚至有可能想要訪問特定類型的子節點以執行某些操作。 看看ANTLR為您生成的解析器。 您會發現一堆*Context類,其中包含訪問每種子節點類型的方法。 例如ctx的參數enterBody()方法是實例BodyContext ,你可以使用所有它的方法來訪問特定類型的子節點。

UPD如果語法僅定義布爾表達式,並且僅將其用於驗證和標記化,則根本不需要解析器。 只需使用lexer即可獲取所有令牌的列表:

input_stream = antlr4.FileStream('input.txt')

# Instantiate an run generated lexer
lexer = BooleanLexer(input_stream)
tokens = antlr4.CommonTokenStream(lexer)

# Parse all tokens until EOF
tokens.fill()

# Print tokens as text (EOF is stripped from the end)
print([token.text for token in tokens.tokens][:-1])

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM