鱼C论坛

 找回密码
 立即注册
查看: 1685|回复: 15

[已解决]两个txt文件内容中重复词的对比 求助

[复制链接]
发表于 2022-8-17 00:26:21 | 显示全部楼层 |阅读模式
8鱼币
您好,我有两个文件内容的比对小问题想请大家帮助,帖子内容看起来呜呜喳喳的有点多,其实很简单,希望大家看一下,万分感谢。

具体而言如下:
我有两个文件A.txt和B.txt(均已在下方附件中给到):

A.txt(内容示例与格式):
{A}
{B}
{C}
{D}                                        格式:(一个集合一行。)
{E}
{F}

B.txt(内容示例与格式):
有两行内容分别是:

整体词:部分词                    格式:(整体词和部分词 以“:”隔开,上述A.txt内的一些集合之间 构成了B.txt的内容,换句话说B.txt的内容都在A.txt内,只是排序不一样。)
{A}:G,{E}#G,{F}                格式:(“:”后面的部分词以#隔开,每个集合前面都有标示的"G,"或者“H,”或者“BM,”等总计三种标识,这三个标识不参与词汇间的比对!不参与!不参与!)
{B}:G,{E}#G,{F}                格式:(“:”后面的部分词中有很多重复的集合,如{A},{B}的部分词是一样的。)
{C}:H,{I}#BM,{J}               
{F}:H,{Q}

代码内容对比要求:
把B.txt中的每一行分别与A.txt中的内容循环对比,若有匹配到,那么给予其“:"前或后的一行内容。生成一个C.txt,其有五行内容,分别是:
结果示例:

A.txt中的全部词汇                是否有整体词                整体词                是否有部分词                部分词               
{A}                                                0                            0                                1                         G,{E}#G,{F}
{B}                                                0                            0                                1                         G,{E}#G,{F}
{C}                                                0                            0                                1                         H,{I}#BM,{J}       
{D}                                                0                            0                                0                             0       
{E}                                                1                        {A}#{B}                        0                             0
{F}                                                1                        {A}#{B}                        1                         H,{Q}


A.txt中的全部词汇(这一行需要严格按照原来的顺序,不想搞混)

结果是这个样子的。最后生成的C是txt或者excel表都行。其实,说白了就是把B.txt内的两行词汇分别对比A.txt的内容给,之后给予了重新编排(请对比看B.txt中的一行内容:{A}:G,{E}#G,{F}与上面的结果示例结果,一看便知)。说的可能还不够简练,不过希望您能看下,很有规律可循。

我要求的结果,有点让大家费脑子了,不过找到规律的话对大家而言一定是小case,希望您练个手,帮助搞一下,再次感谢,Wish you have a nice day....


附件:
A.txt (107.15 KB, 下载次数: 5)
B.txt (85.88 KB, 下载次数: 5)

最佳答案
2022-8-17 00:26:22
比对完了,代码如下:
  1. import re
  2. from collections import OrderedDict

  3. from openpyxl import Workbook

  4. regex = re.compile(r'{.*?}')


  5. class Entry:
  6.     """自定义Entry类,用于记录比对结果"""

  7.     def __init__(self) -> None:
  8.         self.has_full_word = "0"
  9.         self.full_word = "0"
  10.         self.has_partial_word = "0"
  11.         self.partial_word = "0"


  12. # 打开A.txt并读取其全部内容
  13. with open("A.txt", encoding="utf-8") as f:
  14.     lines = f.readlines()

  15. # 数据清洗,每一条数据都清理开头和结尾不必要空白部分
  16. # 变量database既作为数据库是匹配的依据
  17. # 也用来记录结果,避免顺序被打乱
  18. database = OrderedDict()
  19. for entry in lines:
  20.     database[entry.strip()] = Entry()  # 比对结果用Entry对象保存

  21. # 打开B.txt并读取其全部内容
  22. with open("B.txt", encoding="utf-8") as f:
  23.     data_pairs = f.readlines()

  24. # 跳过首行
  25. data_pairs = data_pairs[1:]
  26. # 数据清洗,把每一行都拆分为 整体词 和 部分词 两部分,结构如下
  27. # [[整体词, 部分词], [整体词, 部分词], ...]
  28. for idx, entry in enumerate(data_pairs):
  29.     data_pairs[idx] = entry.strip().split(":")

  30. # 开始匹配
  31. for full_word, partial_word in data_pairs:
  32.     # 是否有 部分词
  33.     if full_word in database:  # 整体词出现在database中则其具有部分词
  34.         database[full_word].has_partial_word = "1"
  35.         database[full_word].partial_word = partial_word

  36.     # 对 部分词 这一列进行拆分并遍历,判断是否具有 整体词
  37.     for item in regex.findall(partial_word):
  38.         if item in database:  # 如果 部分词 的子集合出现在database中
  39.             database[item].has_full_word = "1"  # 标记该子集合具有 整体词
  40.             fw = database[item].full_word
  41.             database[item].full_word = "#".join((fw, full_word))  # 增加整体词

  42. # 准备将database记录的结果写入文件
  43. wb = Workbook()
  44. ws = wb.active
  45. ws.append(['A.txt中的全部词汇', '是否有整体词', '整体词', '是否有部分词', '部分词'])
  46. for k, v in database.items():
  47.     ws.append([k, v.has_full_word, v.full_word.strip('0#'),
  48.               v.has_partial_word, v.partial_word])
  49. wb.save('C.xlsx')
复制代码


其中openpyxl属于第三方库,用于操作Excel表格,需要额外安装。
如果逻辑上我还是理解有误请告知,文件附后,请注意解压。

最佳答案

查看完整内容

比对完了,代码如下: 其中openpyxl属于第三方库,用于操作Excel表格,需要额外安装。 如果逻辑上我还是理解有误请告知,文件附后,请注意解压。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2022-8-17 00:26:22 | 显示全部楼层    本楼为最佳答案   
比对完了,代码如下:
  1. import re
  2. from collections import OrderedDict

  3. from openpyxl import Workbook

  4. regex = re.compile(r'{.*?}')


  5. class Entry:
  6.     """自定义Entry类,用于记录比对结果"""

  7.     def __init__(self) -> None:
  8.         self.has_full_word = "0"
  9.         self.full_word = "0"
  10.         self.has_partial_word = "0"
  11.         self.partial_word = "0"


  12. # 打开A.txt并读取其全部内容
  13. with open("A.txt", encoding="utf-8") as f:
  14.     lines = f.readlines()

  15. # 数据清洗,每一条数据都清理开头和结尾不必要空白部分
  16. # 变量database既作为数据库是匹配的依据
  17. # 也用来记录结果,避免顺序被打乱
  18. database = OrderedDict()
  19. for entry in lines:
  20.     database[entry.strip()] = Entry()  # 比对结果用Entry对象保存

  21. # 打开B.txt并读取其全部内容
  22. with open("B.txt", encoding="utf-8") as f:
  23.     data_pairs = f.readlines()

  24. # 跳过首行
  25. data_pairs = data_pairs[1:]
  26. # 数据清洗,把每一行都拆分为 整体词 和 部分词 两部分,结构如下
  27. # [[整体词, 部分词], [整体词, 部分词], ...]
  28. for idx, entry in enumerate(data_pairs):
  29.     data_pairs[idx] = entry.strip().split(":")

  30. # 开始匹配
  31. for full_word, partial_word in data_pairs:
  32.     # 是否有 部分词
  33.     if full_word in database:  # 整体词出现在database中则其具有部分词
  34.         database[full_word].has_partial_word = "1"
  35.         database[full_word].partial_word = partial_word

  36.     # 对 部分词 这一列进行拆分并遍历,判断是否具有 整体词
  37.     for item in regex.findall(partial_word):
  38.         if item in database:  # 如果 部分词 的子集合出现在database中
  39.             database[item].has_full_word = "1"  # 标记该子集合具有 整体词
  40.             fw = database[item].full_word
  41.             database[item].full_word = "#".join((fw, full_word))  # 增加整体词

  42. # 准备将database记录的结果写入文件
  43. wb = Workbook()
  44. ws = wb.active
  45. ws.append(['A.txt中的全部词汇', '是否有整体词', '整体词', '是否有部分词', '部分词'])
  46. for k, v in database.items():
  47.     ws.append([k, v.has_full_word, v.full_word.strip('0#'),
  48.               v.has_partial_word, v.partial_word])
  49. wb.save('C.xlsx')
复制代码


其中openpyxl属于第三方库,用于操作Excel表格,需要额外安装。
如果逻辑上我还是理解有误请告知,文件附后,请注意解压。

C.zip

135.13 KB, 下载次数: 2

想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2022-8-17 09:48:06 | 显示全部楼层
我需要的最终结果可能有点复杂了,在此简化一下(这样就很简单了):

最终结果是两个文件C.txt和D.txt:

C.txt的内容示例:
A.txt中的全部词汇                整体词
{A}                                           0
{B}                                           0
{C}                                            0
{D}                                           0                                       
{E}                                        {A}#{B}
{F}                                        {A}#{B}


D.txt的内容示例:
A.txt中的全部词汇                部分词
{A}                                        G,{E}#G,{F}
{B}                                        G,{E}#G,{F}
{C}                                        H,{I}#BM,{J}  
{D}                                    0           
{E}                                        0
{F}                                        H,{Q}

这样分开坐就很简单了,谢谢咯。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2022-8-17 10:36:34 | 显示全部楼层
Amgalang 发表于 2022-8-17 09:48
我需要的最终结果可能有点复杂了,在此简化一下(这样就很简单了):

最终结果是两个文件C.txt和D.txt: ...

我看了你的描述,直接说吧,每个字我都看得懂,合在一起我就不知道你说的什么意思了。你并不是描述不够简洁,而是词不达意!在表述方面,你混淆了“行”与“列”这两个概念,比如描述B.txt的时候你说“有两行内容分别是:”,而实际上明明是两列内容,还有后文的“C.txt,其有五行内容”,这里的行也应该是列。正因如此,我看了你的描述至少两个小时还没完全理清楚你要表达的意思。

这个程序最大的挑战在于猜测你的需求而不在于编写程序。
我一开始觉得你的程序写起来有点挑战,会很有意思,直到花了差不多两个小时整理你的表述还没理解你的判定标准,我真的太菜了
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2022-8-17 11:29:44 | 显示全部楼层
Brick_Porter 发表于 2022-8-17 10:36
我看了你的描述,直接说吧,每个字我都看得懂,合在一起我就不知道你说的什么意思了。你并不是描述不够简 ...

好吧,不好意思哒 鱼友,给你添加的麻烦。我必须还得再严谨一些,在此真心感谢您的支持。
其实就是把B中的两列内容分别和A的内容对比,然后生成两个文件,分别写入B.txt中每一行对应内容的更多信息(更多信息就是指“:”的前后内容)。再次谢谢了。我再努力搞搞吧。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2022-8-17 11:43:11 | 显示全部楼层
有产品经理的潜质了
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2022-8-17 12:42:32 | 显示全部楼层
Amgalang 发表于 2022-8-17 11:29
好吧,不好意思哒 鱼友,给你添加的麻烦。我必须还得再严谨一些,在此真心感谢您的支持。
其实就是把B中 ...

其实吧,我还是想挑战一下的,就是看完你的描述始终没有明白“整体词”和“部分词”的判定标准是什么,这也是整个程序的关键点,只要你说明白了我相信很多人都能写出你这个程序。

例如:对于{A}:G,{E}#G,{F}这条记录来说,按照你的格式(整体词:部分词)来说,{A}不就是整体词吗?
为什么在你的结果示例中却变成了{A}的整体词为0?

归根到底,还是因为你没有说明“整体词”与“部分词”的判定标准,是从格式上划分还是从其他角度划分?还是说我的理解是错的,另有其他判定标准?
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2022-8-17 15:46:20 | 显示全部楼层
Brick_Porter 发表于 2022-8-17 12:42
其实吧,我还是想挑战一下的,就是看完你的描述始终没有明白“整体词”和“部分词”的判定标准是什么,这 ...

感谢您的坚持,这次直接说判定标准:

C.txt 生成于A.txt内容与B.txt中的部分词一列内容的对比。

A.txt中的全部词汇                整体词
{A}                                           0
{B}                                           0
{C}                                            0
{D}                                           0                                       
{E}                                        {A}#{B}
{F}                                        {A}#{B}

判定标准:

微信图片_20220817153030_.jpg
微信图片_20220817153030_.jpg
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2022-8-17 15:51:44 | 显示全部楼层
Letheed 发表于 2022-8-17 11:43
有产品经理的潜质了

哈哈哈 努力努力 当一个经理看看
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2022-8-17 15:57:45 | 显示全部楼层
给你鱼不如给你渔,如果你只想要鱼的话,抱歉,我这里没有那么多
flex和bison了解一下
https://cn.bing.com/search?form= ... &q=flex%26bison
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2022-8-17 17:11:30 | 显示全部楼层
Amgalang 发表于 2022-8-17 15:46
感谢您的坚持,这次直接说判定标准:

C.txt 生成于A.txt内容与B.txt中的部分词一列内容的对比。

为什么{E}对应的是{A}#{B}呢?
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2022-8-17 19:03:45 | 显示全部楼层
Brick_Porter 发表于 2022-8-17 17:11
为什么{E}对应的是{A}#{B}呢?

{E}在B.txt中的部分词一列出现了两次阿,然后各自对应{A}和{B}所以{A}#{B}
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2022-8-17 19:05:36 | 显示全部楼层
人造人 发表于 2022-8-17 15:57
给你鱼不如给你渔,如果你只想要鱼的话,抱歉,我这里没有那么多
flex和bison了解一下
https://cn.bing.c ...

谢谢咯,这是我目前阶段最后一个 问题了,我会学习的,感谢。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2022-8-17 20:46:15 | 显示全部楼层
本帖最后由 ZhKQYu 于 2022-8-17 21:25 编辑

处理过后应该是这样吧
  1. def read_file(filename):
  2.     with open(filename) as f:
  3.         return f.readlines()

  4. def get_word(data, dic):
  5.     new_dic = {}
  6.     for line in data:
  7.         line = line.strip()
  8.         if dic.get(line) != None:
  9.             new_dic[line] = "#".join(dic[line])
  10.         else:
  11.             new_dic[line] = None
  12.     return new_dic


  13. def get_value_key_dic(dic):
  14.     new_dic = {}
  15.     for k, v in dic.items():
  16.         for each in v:
  17.             elements = each.split("#")
  18.             for element in elements:
  19.                 start = element.find("{")
  20.                 end = element.find("}")
  21.                 if new_dic.get(element[start:end+1]) == None:
  22.                     new_dic[element[start:end+1]] = []
  23.                 new_dic[element[start:end+1]].append(k)
  24.     return new_dic


  25. def write_file(filename, k_v, v_k, data):
  26.     with open(filename, "w") as f:
  27.         for line in data:
  28.             line = line.strip()
  29.             if k_v[line] != None and v_k[line] != None:
  30.                 f.write("{}#**#{}#**#{}#**#{}#**#{}\n".format(line, 1, v_k[line], 1, k_v[line]))
  31.             elif k_v[line] != None and v_k[line] == None:
  32.                 f.write("{}#**#{}#**#{}#**#{}#**#{}\n".format(line, 0, 0, 1, k_v[line]))
  33.             elif v_k[line] != None and k_v[line] == None:
  34.                 f.write("{}#**#{}#**#{}#**#{}#**#{}\n".format(line, 1, v_k[line], 0, 0))
  35.             else:
  36.                 f.write("{}#**#{}#**#{}#**#{}#**#{}\n".format(line, 0, 0, 0, 0))

  37. def get_key_value_dic(data):
  38.     dic = {}
  39.     for line in data:
  40.         line = line.strip()
  41.         key, value = line.split(':', 1)
  42.         if dic.get(key) == None:
  43.             dic[key] = []
  44.         dic[key].append(value)
  45.     return dic
  46.             

  47. def main():
  48.     file_a = read_file('A.txt')
  49.     file_b = read_file('B.txt')

  50.     key_value_dic = get_key_value_dic(file_b)
  51.     part_dic = get_word(file_a, key_value_dic)

  52.     value_key_dic = get_value_key_dic(key_value_dic)
  53.     all_dic = get_word(file_a, value_key_dic)
  54.     write_file("C.txt", part_dic, all_dic, file_a)

  55. if __name__ == '__main__':
  56.     main()
复制代码

C.txt

336.4 KB, 下载次数: 3

想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2022-8-18 10:43:41 | 显示全部楼层
ZhKQYu 发表于 2022-8-17 20:46
处理过后应该是这样吧

收到了,完美解决,真的很感谢您,我好好学习代码。祝你万事如意,14#的朋友为这个问题跟我讨论了好长时间,所以最佳答案 我给他了。希望理解。再次感谢。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2022-8-18 10:47:32 | 显示全部楼层
ZhKQYu 发表于 2022-8-17 20:46
处理过后应该是这样吧

您好,收到了,完美解决了我的问题,真的很感谢您的帮助。这次之后我也学到了要更加简练,清晰的说出自己需求的必要性,再次感谢您的帮助。祝你万事如意....
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2024-4-16 15:43

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表