1

有没有办法对 ply lexer 规则进行特殊处理?

t_IDENT     = r'[a-zA-Z_][0-9a-zA-Z_]*'
t_OPERATOR  = r'[<>=/*+-]+'
t_DEFINE    = r'='
t_PRODUCES  = r'=>'

我想将运算符定义为列出的字符的任意组合,但自己的特殊情况。例如:==>

a + b
# IDENT('a') OPERATOR('+') IDENT('b') 

a ++=--> b
# IDENT('a') OPERATOR('++=-->') IDENT('b') 

a == b
# IDENT('a') OPERATOR('==-->') IDENT('b') 

a => b
# IDENT('a') PRODUCES('=>') IDENT('b') 

a = b
# IDENT('a') DEFINE('=') IDENT('b') 

a >= b
# IDENT('a') OPERATOR('>=') IDENT('b') 

a <=> b
# IDENT('a') OPERATOR('<=>') IDENT('b') 
4

2 回答 2

2

是的,您获得OPERATOR令牌而不是预期PRODUCES/的原因DEFINE是 PLY 词法分析器的令牌优先规则:

在内部,lex.py 使用该re模块进行其模式匹配。构建主正则表达式时,按以下顺序添加规则:

  1. 函数定义的所有标记都按照它们在词法分析器文件中出现的顺序添加。
  2. 接下来添加由字符串定义的标记,方法是按正则表达式长度递减的顺序对它们进行排序(首先添加较长的表达式)。

只需将某些规则转换为函数:

def t_DEFINE(t):
    r'='
    return t

def t_PRODUCES(t):
    r'=>'
    return t
于 2014-07-20T23:16:25.757 回答
0

我删除了自动t_DEFINEt_PRODUCES规则,并使用保留字技术来处理特殊情况:

special_operators = {'=': 'DEFINE',
                     '=>': 'PRODUCES'}

def t_OPERATOR(t):
    r'[<>=/*+-]+'
    t.type = special_operators.get(t.value, t.type)
    return t
于 2014-07-20T23:25:01.973 回答