zoukankan      html  css  js  c++  java
  • Linux shell 计算两个文件的并集、交集、差集

     假设我们现在有两个文件 a.txt 、b.txt

    a.txt 中的内容如下:

    1
    2
    3
    4
    5
    6
    a
    c
    1
    3
    d
    4

    b.txt 中的内容如下:

    1
    2
    3
    4
    5
    6
    a
    b
    e
    2
    1
    5

    # Example 01

    计算并集:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    [root@VM_81_181_centos ~]# sort -u a.txt b.txt
    1
    2
    3
    4
    5
    a
    b
    c
    d
    e
    [root@VM_81_181_centos ~]#

    # Exmaple 02

    计算交集:

    1
    2
    3
    4
    [root@VM_81_181_centos ~]# grep -F -f a.txt b.txt | sort | uniq
    1
    a
    [root@VM_81_181_centos ~]#

    # Example 03

    计算差集(a - b):

    1
    2
    3
    4
    5
    6
    [root@VM_81_181_centos ~]# grep -F -v -f b.txt a.txt | sort | uniq
    3
    4
    c
    d
    [root@VM_81_181_centos ~]#

    # Example 04 

    计算差集(b - a):

    1
    2
    3
    4
    5
    6
    [root@VM_81_181_centos ~]# grep -F -v -f a.txt b.txt | sort | uniq
    2
    5
    b
    e
    [root@VM_81_181_centos ~]#

    -----------------------------------------------------------手动分割线---------------------------------------------------------------------------

    2018/09/30 更新

    上面介绍了关于如何使用 grep 命令实现文件的交、差集,但是在实际操作中得到的结果却有点问题存在

    1
    2
    3
    4
    5
    [root@VM_81_181_centos ~]# grep -F -f a.txt b.txt | sort | uniq | wc -l
    4095
    [root@VM_81_181_centos ~]# grep -F -f b.txt a.txt | sort | uniq | wc -l
    4729
    [root@VM_81_181_centos ~]#

    上面的命令我是用于求 a 、b 两个文件的交集,但是当把两个文件的位置顺序改变了一下,结果竟然是不

    一样,这是不科学的。

    后来仔细想了想,grep 命令是搜索查找的命令,举个例子:

    c.txt 文件里面的内容如下:

    1
    2
    3
    4
    1122
    1133
    1144
    1155

    d.txt 文件里面的内容如下:

    1
    11223344

    执行 grep 命令:

    1
    2
    3
    4
    [root@VM_81_181_centos ~]# grep -F -f c.txt d.txt | sort | uniq
    11223344
    [root@VM_81_181_centos ~]# grep -F -f d.txt c.txt | sort | uniq
    [root@VM_81_181_centos ~]#

    根据结果,对第一条命令的解读是:

    命令执行后,在 d.txt 文件里面搜索和 c.txt 文件相匹配的字符,因为 c.txt 文件里面的字符 1122 和 d.txt 文件里面的

    字符 11223344 前面的 1122 相匹配,则就把 11223344 字符作为两个文件相同的部分记录下来

    第二条命令:

    命令执行后,在 c.txt 文件里面搜索和 d.txt 文件相匹配的字符,d.txt 文件里面的 11223344 在 c.txt 文件里面找不到

    与其类似或相同的字符,所以,结果为空。

    现在,在 c.txt 文件里面新增字符 112233445566,结果及操作如下:

    c.txt 文件内容:

    1
    2
    3
    4
    5
    1122
    1133
    1144
    1155
    1122334455

    执行  grep 命令:

    1
    2
    3
    [root@VM_81_181_centos ~]# grep -F -f d.txt c.txt | sort | uniq
    1122334455
    [root@VM_81_181_centos ~]#

    结论:

    1
    grep -F -f fileA fileB | sort | uniq

    当 fileA 文件 在前,则表示在 fileB  文件里面搜索和 fileA 文件里面相同或者类似的字符,并将 fileB 文件里面那个字符记录下来

    同理,fileB 在前,fileA 在后的情况。

    但是,在这里这并不是我们想要的结果,我们想要的结果就是我们以前学数学时候,求两个集合的交集一样,结果输

    出的是两个集合共有的部分,尝试了几个方法,最后还是选择使用 cat 命令。

    命令格式如下:

    1
    2
    cat fileA fileB | sort | uniq -d  # 求交集
    cat fileA fileB | sort | uniq -u  # 求差集

    这个命令比较好理解,cat 命令先把两个文件合并成一个文件,然后在对合并后的文件进行排序、去重,-d 命令输出文

    件中相同的字符,-u 命令输出文件中不同的字符,并且 在计算交集的时候 fileA、fileB 文件顺序哪个在前在后的结果都是一样的。

    案例如下:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    [root@VM_81_181_centos ~]# cat c.txt
    1122
    1133
    1144
    1155
    1122334455
    [root@VM_81_181_centos ~]# cat d.txt
    11223344
    1122
    [root@VM_81_181_centos ~]#

    c、d 文件内容如上

    执行 cat 命令求交集:

    1
    2
    3
    4
    5
    [root@VM_81_181_centos ~]# cat c.txt d.txt | sort | uniq -d
    1122
    [root@VM_81_181_centos ~]# cat d.txt c.txt | sort | uniq -d
    1122
    [root@VM_81_181_centos ~]#

    执行 cat 命令求差集:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    [root@VM_81_181_centos ~]# cat c.txt d.txt | sort | uniq -u
    11223344
    1122334455
    1133
    1144
    1155
    [root@VM_81_181_centos ~]# cat d.txt c.txt | sort | uniq -u
    11223344
    1122334455
    1133
    1144
    1155
    [root@VM_81_181_centos ~]#

    但是 cat 命令也有一个短板,当文件比较大的时候,就会出错,但是在这里我们可以去借助

  • 相关阅读:
    (转)LayoutInflater的使用
    SQLite入门
    字符排序 分类: java 20100103 14:28 791人阅读 评论(1) 收藏
    oracle常用日期函数 20091211 22:13 300人阅读 评论(0) 收藏
    several years later 分类: 人生墨客 20100106 12:29 470人阅读 评论(0) 收藏
    值传递与引用传递 分类: java 20091218 21:41 343人阅读 评论(0) 收藏
    第一章 基本知识 分类: java 20091229 16:49 307人阅读 评论(0) 收藏
    第三章 运算符、表达式与语句 分类: java 20091229 16:46 304人阅读 评论(0) 收藏
    第五章 继承、接口与泛型 分类: java 20091229 16:43 348人阅读 评论(0) 收藏
    第二章 基本数据类型,输入、输出,数组 分类: java 20091229 16:48 339人阅读 评论(0) 收藏
  • 原文地址:https://www.cnblogs.com/zhichao123/p/12591454.html
Copyright © 2011-2022 走看看