词法分析

0 投票
2 回答
829 浏览
提问于 2025-04-18 00:13

我正在学习Python中的词法分析器,使用Ply库来对一些字符串进行词法分析。我实现了一个词法分析器,用来处理一些C++语言的语法。

不过,我遇到了一些奇怪的情况。当我把COMMENT 状态函数定义放在其他函数定义的后面时,代码运行得很好。但如果我把COMMENT 状态函数放在其他定义之前,输入字符串一旦开始出现//注释部分,就会报错。

这背后是什么原因呢?

import ply.lex as lex

tokens = (
        'DLANGLE',       # <<
        'DRANGLE',       # >>
        'EQUAL',        # =
        'STRING',       # "144"
        'WORD',         # 'Welcome' in "Welcome."
        'SEMICOLON',    # ;

)

t_ignore                = ' \t\v\r' # shortcut for whitespace


states = (
        ('cppcomment', 'exclusive'),   # <!--
)



def t_cppcomment(t): # definition here causes errors
    r'//'
    print 'MyCOm:',t.value

    t.lexer.begin('cppcomment');



def t_cppcomment_end(t):
    r'\n'
    t.lexer.begin('INITIAL');


def t_cppcomment_error(t):
    print "Error FOUND"
    t.lexer.skip(1)

def t_DLANGLE(t):

    r'<<'
    print 'MyLAN:',t.value
    return t

def t_DRANGLE(t):
    r'>>'
    return t

def t_SEMICOLON(t):

    r';'
    print 'MySemi:',t.value
    return t;

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

def t_STRING(t):
        r'"[^"]*"'
        t.value = t.value[1:-1] # drop "surrounding quotes"
        print 'MyString:',t.value
        return t

def t_WORD(t):
        r'[^ <>\n]+'
        print 'MyWord:',t.value
        return t




webpage = "cout<<\"Hello World\"; // this comment"
htmllexer = lex.lex()
htmllexer.input(webpage)
while True:
        tok = htmllexer.token()
        if not tok: break
        print tok

祝好

2 个回答

0

这是因为你没有任何规则来处理 thiscomment。其实你并不在乎评论里面有什么,你可以很简单地做一些事情,比如:

t_cppcomment_ANYTHING = '[^\r\n]'

就放在你的 t_ignore 规则下面。

1

我刚刚搞明白了。因为我把评论状态定义为 exclusive(独占),所以它不会使用 inclusive(包含)的状态模块(如果评论模块在最上面定义的话,反正它会用上)。所以你需要重新定义所有的评论状态模块。因此,ply 提供了 error() 模块,用来跳过那些没有特定模块定义的字符。

撰写回答