python - 如何简化这些布尔语句
问题描述
我被告知要以更简化的形式在 python 中压缩它。是否可以有条不紊地进行?
(not ((b or not c) and (not a or not c))) or (not (c or not (b and c))) or (a and not c) and (not a or (a and b and c) or (a and ((b and not c) or (not b))))
(not (a and not b) or (not c and b)) and (not b) or (not a and b and not c) or (a and not b))
解决方案
您可以使用 sympy 来评估和简化布尔表达式:
(注意:本例中的解析器相当幼稚):
from sympy.logic.boolalg import to_dnf
from sympy.abc import a, b, c
def translate(expr):
e = list(expr)
res = [' ' for _ in range(len(e))]
for start in range(len(e)):
if expr[start: start+3] == 'not':
res[start] = '~'
res[start+1] = ''
res[start+2] = ''
elif expr[start: start+3] == 'and':
res[start] = '&'
res[start+1] = ''
res[start+2] = ''
else:
if res[start] == ' ':
res[start] = e[start]
expr = ''.join(res)
e = list(expr)
res = [' ' for _ in range(len(e))]
for start in range(len(e)):
if expr[start: start+2] == 'or':
res[start] = '|'
res[start+1] = ''
else:
if res[start] == ' ':
res[start] = e[start]
res = [elt for elt in res if elt != ' ' or elt != '']
return ''.join(res)
exp1 = '(not ((b or not c) and (not a or not c))) or (not (c or not (b and c))) or (a and not c) and (not a or (a and b and c) or (a and ((b and not c) or (not b))))'
exp2 = '(not (a and not b) or (not c and b)) and (not b) or (not a and b and not c) or (a and not b)'
print('exp1:', '\n', eval(translate(exp1)), '\n', to_dnf(eval(translate(exp1)), simplify=True))
print('exp2:', '\n', eval(translate(exp2)), '\n', to_dnf(eval(translate(exp2)), simplify=True))
输出简化的表达式
exp1:
~(c | ~(b & c)) | ~((b | ~c) & (~a | ~c)) | (a & ~c & (~a | (a & b & c) | (a & (~b | (b & ~c)))))
a | (c & ~b)
exp2:
(a & ~b) | (b & ~a & ~c) | (~b & ((b & ~c) | ~(a & ~b)))
~b | (~a & ~c)
正确性验证:
对于每个输入,评估原始表达式和简化表达式的真值表。
def evaluate(a, b, c):
exp1 = (not ((b or not c) and (not a or not c))) or (not (c or not (b and c))) or (a and not c) and (not a or (a and b and c) or (a and ((b and not c) or (not b))))
exp2 = (not (a and not b) or (not c and b)) and (not b) or (not a and b and not c) or (a and not b)
return exp1, exp2
def evaluate2(a, b, c):
exp1 = a or (c and not b)
exp2 = not b or (not a and not c)
return exp1, exp2
values = [(1, 1, 1), (1, 1, 0), (1, 0, 1), (0, 1, 1), (1, 0, 0), (0, 1, 0), (0, 0, 1), (0, 0, 0)]
for vals in values:
print(f'{vals}: {evaluate(*vals)}, {evaluate2(*vals)}')
真值表输出:
(1, 1, 1): (True, False), (1, False)
(1, 1, 0): (True, False), (1, False)
(1, 0, 1): (True, True), (1, True)
(0, 1, 1): (0, 0), (False, False)
(1, 0, 0): (True, True), (1, True)
(0, 1, 0): (0, True), (0, True)
(0, 0, 1): (True, True), (True, True)
(0, 0, 0): (0, True), (0, True)
推荐阅读
- python - 如何将 keras 模型与其他数据一起保存并完全加载?
- python - PUDB 错误:
- selenium - 并行执行失败。它在一个会话和另一个会话上成功执行测试,没有执行任何操作
- spring - X-application-context-header 未传递给 openshift/liberty 中的 httpHeaders Map
- python - 与用于逻辑回归的 Scikit-Learn 相比,Tensorflow 的性能要差得多
- postgresql - postgresql 函数根据 IF ELSEIF 条件更新每一行
- json - JSON 格式不正确
- css - 当其容器/父元素悬停时将css样式应用于元素
- dart - 通过滑动更改路线
- selenium - Selenium ChromeDriver 异常