我有一个布尔表达式字符串,我想分开:
condition = "a and (b or (c and d))"
或者让我们说:
我希望能够访问两个括号之间的字符串内容
我想要以下结果:
"(b or (c and d))"
"(c and d)"
我已尝试使用正则表达式(不是真的有效)
x = re.match(".*(\(.*\))", condition)
print x.group(1)
问题:
将布尔表达式字符串分开的最好方法是什么?
答案 0 :(得分:8)
这是一种简单的正则表达式无法做到的事情。您需要实际解析文本。 pyparsing显然非常适合这样做。
答案 1 :(得分:2)
就像每个人都说的那样,你需要一个解析器。
如果您不想安装,可以从this simple top-down parser开始(采取最后一个代码示例here)
删除与您的需求无关的所有内容(+, - ,*,/,是,lambda,if,else,...)。只需保留括号and
,or
即可。
您将获得从表达式生成的二叉树结构。
标记生成器使用内置tokenize
(import tokenize
),这是一个Python源代码的词法扫描程序,但对于像你这样的简单案例可以正常工作。
答案 2 :(得分:2)
如果您的要求非常简单,那么您并不需要解析器。 使用堆栈可以很容易地实现匹配括号。
您可以执行以下操作:
condition = "a and (b or (c and d))"
stack = []
for c in condition:
if c != ')':
stack.append(c)
else:
d = c
contents = []
while d != '(':
contents.insert(0, d)
d = stack.pop()
contents.insert(0, d)
s = ''.join(contents)
print(s)
stack.append(s)
产生
(c and d)
(b or (c and d))
答案 3 :(得分:0)
构建解析器:
Condition ::= Term Condition'
Condition' ::= epsilon | OR Term Condition'
Term ::= Factor Term'
Term' ::= epsilon | AND Factor Term'
Factor ::= [ NOT ] Primary
Primary ::= Literal | '(' Condition ')'
Literal ::= Id