Linux / Shell切片大文本文件

时间:2019-06-22 03:29:18

标签: linux bash awk grep

给予

File1

uniquename1:somethinguseless:somethinguseless:uniquekey1
uniquename2:somethinguseless:somethinguseless:uniquekey2
uniquename3:somethinguseless:somethinguseless:uniquekey3

File2

uniquekey1:hello
uniquekey2:apple
uniquekey3:hello

我希望制作一种基本上可以做到这一点的方法

$ command uniquename2
apple
$ command uniquename1
hello
$ command uniquename3
hello

因此给定文件1中的唯一名称,它将使用文件2中的密钥来获取其链接。如果找不到唯一名称,则不执行任何操作。

我的尝试

$ grep -i 'uniquename1' | (not sure how to slice the line with regex "*:*:*") | grep $thisline file2

4 个答案:

答案 0 :(得分:1)

sed使此操作相对容易。例如:

$ sed -n "/$(sed -n '/uniquename2/s/.*[:]//p' file1)/s/.*[:]//p" file2
apple

$ sed -n "/$(sed -n '/uniquename3/s/.*[:]//p' f1)/s/.*[:]//p" f2
hello

您只是使用命令替换 $(sed -n '/uniquename3/s/.*[:]//p' f1)uniquekey中获得uniquename,所以它会修剪行的开头部分,然后执行相同的操作返回结果以使用外部的双引号使用sed -n "/$(command)/s/.*[:]//p"获得想要的字符串,以允许命令替换扩展。

使用的基本sed命令的形式是普通替换s/find/replace,其前导模式匹配为总计

sed '/match/s/find/replace/`

-n禁止模式空间的正常打印,而最后的p导致匹配和替换成功时进行打印。

如果uniquenameuniquekey包含正则表达式字符

鉴于您对实际文件返回错误的评论,实际文件中的每个uniquenameuniquekey都包含可被解释为正则表达式的字符。在那种情况下,例如,使用awk变量的GNU FILENAME解决方案应能基于':'分隔的字段从每个文件中提取所需的信息。

$ awk -F: -v name=uniquename2 '
    FILENAME == "file1" { $1 == name && key = $NF } 
    FILENAME == "file2" { if ($1 == key) print $NF }
' file1 file2
apple

如果您有任何问题,请告诉我。另外,如果您可以发布file1file2的一些实际示例(每个示例10行),那会有所帮助。

答案 1 :(得分:1)

这里有一个awk脚本,它只扫描两个文件一次。与嵌套grep解决方案不同,它执行uniqueId * (uniqueId - 1)文件扫描。

script.awk

BEGIN {FS=":"} # field separator is :
FNR == NR && $1 == keyArg {id = $NF} # find the id in first file
FNR == NR {next} # continue scanning first file
$1 == id {print $2} # find the id in second file and print its 2nd field value

执行:

 awk -v keyArg="uniquename2" -f script.awk file1 file2 

答案 2 :(得分:1)

正确的答案是这样的:

$ awk -v tgt='uniquename2' -F':' 'NR==FNR{map[$1]=$2; next} $1==tgt{print map[$NF]}' file2 file1
apple

或几乎(请参见下面的评论)what @DudiBoy posted

答案 3 :(得分:0)

cut实用程序是为此类数据设计的:

#!/bin/bash
KEY=$(grep -i -e "^$1:" file1.txt | cut -d ':' -f 4)
grep -e "^$KEY" file2.txt | cut -d ':' -f 2