这是我在这里发表的第一篇文章,我希望我的问题清晰,格式正确......
我有两本词典。第一本字典包含我正在调用的内容" Option Expressions"作为值的键和任意项:dict1 = {'((opt1 OR opt4 OR opt6) AND NOT opt7)': 'Yellow Roof', '((opt2 AND opt3) XOR opt5': 'Purple Scooter'}
print(dict1)
{'((opt1 OR opt4 OR opt6) AND NOT opt7)': 'Yellow Roof',
'((opt2 AND opt3) XOR opt5': 'Purple Scooter'}
第二个字典包含来自dict1
的选项作为键,以及它们是否为"接受"或"被拒绝"作为价值观:
dict2 = {'opt1': 'Accepted', 'opt2': 'Rejected', 'opt3': 'Rejected','opt4': 'Accepted', 'opt5': 'Accepted', 'opt6': 'Rejected','opt7': 'Accepted'}
print(dict2)
{'opt1': 'Accepted',
'opt2': 'Rejected',
'opt3': 'Rejected',
'opt4': 'Accepted',
'opt5': 'Accepted',
'opt6': 'Rejected',
'opt7': 'Accepted'}
我如何评估dict1
中True
或False
的表达式,以确定根据dict2
中的选项是否选择了哪些项目?接受还是拒绝?
我最初的想法是将表达式中的opt替换为1表示接受,0表示拒绝表示:
((1 OR 1 OR 0) AND NOT 1)
评估为False
和
((0 AND 0) XOR 1)
评估为True
我一直在对pyparsing进行一些研究,并认为它在这里很有用,尽管我并不完全确定如何最好地利用它。
我正在应用布尔逻辑:
AND:当且仅当双方都是真的时才为真
OR:如果任何一方都是真的,则为真
NOT /(AND NOT):将true更改为false,将false更改为true
XOR:如果一方是真的那么是真的(但是 不两者)
答案 0 :(得分:1)
通过对数据进行一点点按摩,您可以将其转换为有效的Python并让Python解释器进行出价:
# Mandatory warning here about using eval() - here be dragons!
dict1 = {"((opt1 OR opt4 OR opt6) AND NOT opt7)": "Yellow Roof",
"((opt2 AND opt3) XOR opt5)": "Purple Scooter"}
dict2 = {"opt1": "Accepted",
"opt2": "Rejected",
"opt3": "Rejected",
"opt4": "Accepted",
"opt5": "Accepted",
"opt6": "Rejected",
"opt7": "Accepted"}
# lets first normalize the 'opt' codes to True/False
dict2_norm = {k: (True if v == "Accepted" else False) for k, v in dict2.items()}
# Now all we need to do is evaluate the expressions:
for expression, value in dict1.items():
# Let's first normalize the expression to Python-digestible
expression = expression.replace("XOR", "is not").replace("OR", "or")\
.replace("AND", "and").replace("NOT", "not")
if eval(expression, dict2_norm):
print(value)
# prints: Purple Scooter
答案 1 :(得分:0)
这是我提出的解决方案。它假设你已经用True和False替换了'Accepted'和'Rejected'(或者像你在问题中所说的那样替换了1和0)。
然后处理结果。它首先将结果格式化为有效的Python代码('xor' - > ^
,'AND' - > and
和'OR' - > or
),替换使用布尔对应物选择值,最后使用eval
内置函数计算表达式。
input_code = '((opt1 OR opt4 OR opt6) AND NOT opt7)'
input_w_xor = '(opt2 AND opt3) XOR opt5'
result_codes = {'opt1': True, 'opt2': False, 'opt3': False,'opt4': True, 'opt5': True, 'opt6': False,'opt7': True}
def process_code(input_code, result_codes):
input_code = input_code.lower()
def replace_op_codes(code):
for opt_key, opt_value in result_codes.items():
code = code.replace(opt_key, str(opt_value))
return code
input_code = replace_op_codes(input_code)
input_code = input_code.replace("xor", '^')
result = eval(input_code)
return result
print(process_code(input_code, result_codes))
print(process_code(input_w_xor, result_codes))
我倾向于回避使用eval
和exec
,但我认为这是这种情况下最快的解决方案。