python实现两个字符串比对差异点

一:代码实现

import difflib, re

# 比较两个文本差异点
def compare_text_index(text1, text2):
    # 创建SequenceMatcher对象
    matcher = difflib.SequenceMatcher(a=text1, b=text2)
    # 获取差异报告
    diff_report = matcher.get_opcodes()
    # 检查差异报告中是否存在关键词错误
    for tag, i1, i2, j1, j2 in diff_report:
        if tag == 'replace':
            print("{0} with {1}".format(text1[i1:i2], text2[j1:j2]))
        elif tag == 'delete':
            # 检查删除操作中是否包含关键词
            print("{0} with {1}".format(text1[i1:i2], text2[j1:j2]))
        elif tag == 'insert':
            # 检查插入操作中是否包含关键词
            print("{0} with {1}".format(text1[i1:i2], text2[j1:j2]))

    return None

text1 = "四位导师通过盲选选择自己心仪的学员组成战队."
text2 = "四位到时候通过盲选选择自己sds的学员组成站队."
compare_text_index(text1,text2)

运行结果:

导师 with 到时候
心仪 with sds
战 with 站

二:实战:按照行比对文本差异点,统计文本中关键词的差异点。

当前需要3个文本:

lable.txt

中国好声音是浙江卫视推出的励志专业音乐评论节目。
节目邀请明星导师言传身教,为中国乐坛的发展提供一批怀揣梦想、具有天赋才华的音乐人 。
四位导师通过盲选选择自己心仪的学员组成战队.
并带领自己的战队进行战队内和战队间关于音乐的对抗。

ocr.txt

中国声音是浙卫视推出的励志专业音乐评论节目。
节目邀请明星到时候言传身教,为中国乐坛的发展提供一批怀揣梦想、具有天赋才华的音乐人 。
四位导师通过盲选选择自己心仪的学员组成站队.
并带领自己的战队进行战队内和战队间关于音乐的对抗。

key_word.txt

中国好声音
浙江卫视
导师
战队

实现代码:

import difflib, re

def read_keyword(txtFile):
    try:
        with open(txtFile, 'r', encoding='utf-8') as file:
            contents = file.readlines()
            contents = [i.replace("\n", "") for i in contents if len(i) > 1]
    except Exception as e:
        with open(txtFile, 'r', encoding='gbk') as file:
            contents = file.readlines()
            contents = [i.replace("\n", "") for i in contents if len(i) > 1]
    return contents


# 比较两个文本差异点
def compare_text_index(text1, text2, keyword):
    # print(text1)
    # print(text2)
    # print(keyword)
    # 创建SequenceMatcher对象
    matcher = difflib.SequenceMatcher(a=text1, b=text2)
    # 获取差异报告
    diff_report = matcher.get_opcodes()
    # 检查差异报告中是否存在关键词错误
    for tag, i1, i2, j1, j2 in diff_report:
        if tag == 'replace':
            # 检查替换操作中是否包含关键词
            if keyword[0] <= i1 <= i2 <= keyword[1]:
                left_num = i1 - keyword[0]
                right_num = keyword[1] - i2
                # return f'Replace "{text1[keyword[0]:keyword[1]]}" with "{text2[j1-left_num:j2+right_num]}"'
                return f'{text1[keyword[0]:keyword[1]]} {text2[j1 - left_num:j2 + right_num]} 0'
        elif tag == 'delete':
            # 检查删除操作中是否包含关键词
            if keyword[0] <= i1 <= i2 <= keyword[1]:
                left_num = i1 - keyword[0]
                right_num = keyword[1] - i2
                return f'{text1[keyword[0]:keyword[1]]} {text2[j1 - left_num:j2 + right_num]} 0'
        elif tag == 'insert':
            # 检查插入操作中是否包含关键词
            if keyword[0] <= i1 <= i2 <= keyword[1]:
                left_num = i1 - keyword[0]
                right_num = keyword[1] - i2
                return f'{text1[keyword[0]:keyword[1]]} {text2[j1 - left_num:j2 + right_num]} 0'
    return None


def keyword_index(ground_truth, substring):
    """

    :param ground_truth: 文本行
    :param substring: 关键词
    :return:
    """
    matches = re.finditer(r'(?={})'.format(re.escape(substring)), ground_truth)
    indices = [match.start() for match in matches]
    indexs = [(i, i + len(substring)) for i in indices]
    return indexs


def remove_corssed_tuples(arr):
    # 按照元组的第一个元素进行排序
    sorted_arr = sorted(arr, key=lambda x: x[0])
    result = [sorted_arr[0]]
    for i in range(1, len(sorted_arr)):
        # 判断前一个元组的第二个元素是否大于后一个元组的第一个元素
        if result[-1][1] > sorted_arr[i][0]:
            # 若存在交叉,则更新前一个元组的第二个元素为较大值
            result[-1] = (result[-1][0], max(result[-1][1], sorted_arr[i][1]))
        else:
            # 若不存在交叉,则直接添加元素
            result.append(sorted_arr[i])

    return result


if __name__ == '__main__':
    lable_txt = "lable.txt"
    ocr_txt = "ocr.txt"
    key_word_txt = "key_word.txt"
    keyword_list = read_keyword(key_word_txt)
    lable_list = read_keyword(lable_txt)
    ocr_list = read_keyword(ocr_txt)
    for id, lable in enumerate(lable_list):
        text1 = lable
        text2 = ocr_list[id]

        # 获取所有关键词列表
        all_index = []
        for key in keyword_list:
            result_index = keyword_index(text1, key)
            all_index.extend(result_index)
        # 获取所有关键词的索引,去除交叉的索引
        if not all_index:
            continue
        result = remove_corssed_tuples(all_index)
        for index_ in result:
            content = compare_text_index(text1, text2, index_)
            if content:
                print(content)
            # else:
            #     print("文本相同")

运行结果:

中国好声音 中国声音 0
浙江卫视 浙卫视 0
导师 到时候 0
战队 站队 0

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

空弹壳

你的鼓励是我创作的动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值