shell学习之按照某列合并两个文件

来源:互联网 发布:java定义方法 编辑:程序博客网 时间:2024/06/07 04:41
有两个文件:ip_city_location.file 有三个字段存放的是ip,城市和地点。
211.82.96.2  北京  海淀区211.82.96.3  北京  朝阳区211.82.96.5  南阳  卧龙区10.1.18.7  郑州  新郑
文件ip.file中有一个字段存放的是ip
10.1.18.7211.82.96.5
现在要求输出ip.file中的每个ip对应的城市。
解决办法:使用join命令。
注意:在使用join前,需要将两个文件按照相同的规则进行排序,这样才能使用join达到期望的效果
故代码如下:
#!/bin/bash filenameBeforSort1="ip_city_location.file"filenameBeforSort2="ip.file"sortedFile1="ip_city_location.sort"sortedFile2="ip.sort"sort $filenameBeforSort1 > $sortedFile1sort $filenameBeforSort2 > $sortedFile2join $sortedFile1 $sortedFile2 | awk '{print $1,$2}'
运行结果如下:
10.1.18.7 郑州211.82.96.5 南阳
现问题发生了一些变化,ip_city_location.file和ip.file中均有重复的记录。ip_city_location.file内容如下:
211.82.96.2  北京  海淀区211.82.96.3  北京  朝阳区211.82.96.5  南阳  卧龙区211.82.96.3  北京  朝阳区10.1.18.7 郑州  新郑211.82.96.2  北京  海淀区10.1.18.7 郑州  新郑
ip.file的内容变为如下:
10.1.18.7211.82.96.510.1.18.7211.82.96.5
则需要进行去重的工作。可以在join之前对两个文件排序时直接去重,也可以join之后再去重。个人认为排序前去重可能效率更高一点。
join前去重:
#!/bin/bash filenameBeforSort1="ip_city_location.file"filenameBeforSort2="ip.file"sortedFile1="ip_city_location.sort"sortedFile2="ip.sort"sort $filenameBeforSort1 | uniq | sort > $sortedFile1 #第二个sort命令不写效果也一样,但是个人认为加上更保险一些,不过数据量大时也许会影响效率 sort $filenameBeforSort2 |uniq | sort > $sortedFile2 #第二个sort命令不写效果也一样,但是个人认为加上更保险一些,不过数据量大时也许会影响效率 join $sortedFile1 $sortedFile2 | awk '{print $1,$2}'
运行结果如下:
10.1.18.7 郑州211.82.96.5 南阳
join之后去重:
#!/bin/bash filenameBeforSort1="ip_city_location.file"filenameBeforSort2="ip.file"sortedFile1="ip_city_location.sort"sortedFile2="ip.sort"sort $filenameBeforSort1 > $sortedFile1sort $filenameBeforSort2 > $sortedFile2join $sortedFile1 $sortedFile2 | awk '{print $1,$2}' | sort | uniq  #在做uniq命令之前是必须先执行sort命令的
运行结果如下:
10.1.18.7 郑州211.82.96.5 南阳
本文仅仅针对这一个例子的实际解决过程进行了描述,其中使用的是join,sort和uniq命令的简单用法。
join命令,就相当于数据库中的内连接,不指定任何参数的情况下,默认按第一列合并,关键字不匹配的行不会输出。sort命令不指定任何参数的情况下,默认按第一列排序。
join命令还可以指定按照其它列合并。当然对应的,sort的时候也要按指定的列sort才可以达到效果。


0 0