如何在Python中合并括号内值不同的同类字符串
问题描述
我需要处理以下格式的规则字符串列表,合并同类规则的取值:
- 示例输入1:
期望输出1:['COLOR INCLUDES (40)', 'LONG_DESCRIPTION CONTAINS ("BLACK")', 'COLOR INCLUDES (38)']['COLOR INCLUDES (40,38)', 'LONG_DESCRIPTION CONTAINS ("BLACK")'] - 示例输入2:
期望输出2:['COLOR INCLUDES (30,31,32,33,56,74,84,85,93,99,184,800,823,830,833,838,839)', 'COLOR INCLUDES (30,31,32,33,56,74,84,85,93,99,184,409,800,823,830,833,838,839)', 'COLOR INCLUDES (800)']['COLOR INCLUDES (30,31,32,33,56,74,84,85,93,99,184,409,800,823,830,833,838,839)'] - 特殊情况:部分规则取值不带括号,例如
['FAMILY EQUALS 1145']
我尝试过两种方法,但都没找到合适的方案:
- 用正则匹配
(之前的字符串,但无法处理无括号的情况; - 使用
suffix_trees库的STree查找最长公共子序列,但不知道如何处理取值和右括号:from suffix_trees import STree st = STree.STree(['COLOR INCLUDES(30,31,32,33,56,74,84,85,93,99,184,800,823,830,833,838,839)', 'COLOR INCLUDES(30,31,32,33,56,74,84,85,93,99,184,409,800,823,830,833,838,839)', 'COLOR INCLUDES (800)']) st.lcs() out: 'COLOR INCLUDES ('
已实现的解决方案
在@stef的建议下,我拆分问题并完成了实现,以下是Rule_process类代码及运行结果:
import re class Rule_process: def __init__(self): self.rules = '(COLOR INCLUDES (40)) OR (LONG_DESCRIPTION CONTAINS ("BLACK")):1|||COLOR INCLUDES (30,31,32,33,56,74,84,85,93,99,184,800,823,830,833,838,839):0|||COLOR INCLUDES (30,31,32,33,56,74,84,85,93,99,184,409,800,823,830,833,838,839):0|||COLOR INCLUDES (40):1|||COLOR INCLUDES (800):0' self.rules_dict = { 0: None, 1: None, 2: None, 4: None, } def append_rules(self): rules = self.rules.split("|||") values_0 = [] values_1 = [] values_2 = [] values_4 = [] for rule in rules: suffix = rule[-1] if suffix == '0': values_0.append(rule[:-2]) elif suffix == '1': values_1.append(rule[:-2]) elif suffix == '2': values_2.append(rule[:-2]) elif suffix == '4': values_4.append(rule[:-2]) if values_0: self.rules_dict[0] = values_0 if values_1: self.rules_dict[1] = values_1 if values_2: self.rules_dict[2] = values_2 if values_4: self.rules_dict[4] = values_4 regex = r'^\(' for key in self.rules_dict.keys(): current_rules = self.rules_dict[key] if current_rules is None: continue processed = [] for rule in current_rules: sub_rules = rule.split(' OR ') cleaned = [] for r in sub_rules: r = r.replace("))", ")") r = re.sub(regex, "", r) cleaned.append(r) processed.extend(cleaned) # 去重后更新 self.rules_dict[key] = list(set(processed)) return self.rules_dict def split_rule(self): # 示例解析:COLOR INCLUDES (30,31,32,33) -> name='COLOR INCLUDES', values=[30,31,32,33] # LONG_DESCRIPTION CONTAINS ("BLACK") -> name='LONG_DESCRIPTION CONTAINS', values='"BLACK"' new_dict = { 0: None, 1: None, 2: None, 4: None, } for key in self.rules_dict.keys(): current_rules = self.rules_dict[key] if current_rules is None: continue pql_dict = {} for rule in current_rules: # 拆分规则名称和取值部分 name_part, value_part = rule.rsplit(maxsplit=1) # 清理取值部分的括号 value_str = value_part.replace("(", "").replace(")", "") try: # 尝试转为整数列表 values = list(map(int, value_str.split(","))) except ValueError: # 非数值类型直接保留原字符串 values = value_str # 合并同类规则的取值并去重 if name_part in pql_dict: if isinstance(values, list): pql_dict[name_part].extend(values) pql_dict[name_part] = list(set(pql_dict[name_part])) else: # 非列表类型直接保留(避免重复添加) if values not in pql_dict[name_part]: pql_dict[name_part].append(values) else: pql_dict[name_part] = values if isinstance(values, list) else [values] # 重新组装规则字符串 assembled = [] for name, vals in pql_dict.items(): if isinstance(vals, list): # 列表类型用方括号包裹 rule_str = f"{name} {vals}" else: rule_str = f"{name} {vals}" assembled.append(rule_str) new_dict[key] = assembled self.rules_dict = new_dict
运行结果
process = Rule_process() process.append_rules() process.split_rule() process.rules_dict OUT: {0: ['COLOR INCLUDES [32, 33, 800, 99, 833, 838, 839, 74, 84, 85, 30, 823, 184, 409, 56, 93, 830, 31]'], 1: ['COLOR INCLUDES [40]', 'LONG_DESCRIPTION CONTAINS "BLACK"'], 2: None, 4: None}
内容的提问来源于Stack Exchange,提问作者LuisGT
相关产品推荐
相关产品推荐

