可以用python ast模块吗?
我想写一个程序,用来修改Python程序,具体是这样的:
把
"某个固定字符串 %" % SOMETHING
改成
functioncall("某个固定字符串 %") % SOMETHING
谢谢!
4 个回答
1
你可以不写程序就解决这个问题。只需使用一个非常棒的编辑器:Emacs。如果你还没学过,真心推荐你去学一下。用它的话,你可以利用它的正则替换功能来解决这个问题。唯一的问题是,我很少用正则表达式,所以总是忘记那些复杂的语法细节,还得去查资料 :P 我会再帮你弄明白的。这里有一个链接,提供了关于Emacs的搜索和替换信息 - 向下滚动可以找到正则表达式的用法
2
使用 tokenize 可能会更简单——我们可以根据文档中的例子来调整一下。
import cStringIO
import tokenize
class Lookahead(object):
def __init__(self, s):
self._t = tokenize.generate_tokens(cStringIO.StringIO(s).readline)
self.lookahead = next(self._t, None)
def __iter__(self):
return self
def next(self):
result = self.lookahead
if result is None: raise StopIteration
self.lookahead = next(self._t, None)
return result
def doit(s):
toks = Lookahead(s)
result = []
for toktype, tokvalue, _, _, _ in toks:
if toktype == tokenize.STRING:
pk = toks.lookahead
if pk is not None and pk[0] == tokenize.OP and pk[1] == '%':
result.extend([
(tokenize.NAME, 'functioncall'),
(tokenize.OP, '('),
(tokenize.STRING, repr(tokvalue)),
(tokenize.OP, ')')
])
continue
result.append((toktype, tokvalue))
return tokenize.untokenize(result)
print doit('"some literal string %" % SOMETHING')
这段代码会输出 functioncall ('"some literal string %"')%SOMETHING
。这里的空格看起来有点奇怪(要把空格调整得恰到好处需要花费很多精力——而且如果你想从修改过的抽象语法树(AST)重建源代码,那就更麻烦了),不过如果你只是想导入或运行生成的代码,那就没问题了(如果你想得到可读性和可编辑性都很好的代码,那就不太好了——不过这是个比较大的问题,我建议另开一个问题来讨论;-)。