合并两个没有伪重复的文件

时间:2015-08-07 19:02:03

标签: linux command-line awk sed

我有两个文本文件file1.txtfile2.txt,它们都包含如下所示的单词行: fare word word-ed wo-ded wor

fa-re text uncial woded wor worded 或类似的东西。总而言之,我的意思是a-z字母的连续可能带有重音符号,以及符号-。我的问题是,如何从这两个满足以下三个条件的文件中从linux命令行创建第三个文件output.txt(使用awksed等):

  1. 如果两个文件中出现相同的单词,则第三个文件output.txt只包含一次。
  2. 如果文件中某个单词的连字符版本(例如file2.txt中的fa-re)出现在另一个单词中,则只有连字符版本会保留在output.txt中(例如,仅{{1}保留在我们的示例中。)
  3. 因此,output.txt应包含以下单词: fa-re

    =====编辑========================

    我修改了文件并给出了输出文件。 我将尝试手动确保没有不同的带连字符的单词(例如wod-ed和wo-ded)。

3 个答案:

答案 0 :(得分:2)

另一个awk:

!($1 in a) || $1 ~ "-" { 
    key = value = $1; gsub("-","",key); a[key] = value 
}
END { for (i in a) print a[i] }

$ awk -f npr.awk file1.txt file2.txt
text
word-ed
uncial
wor
wo-ded
word
fa-re

答案 1 :(得分:1)

Awk Solution

!($1 in words) {
    split($1, f, "-")
    w = f[1] f[2]
    if (f[2])
        words[w] = $1
    else
        words[w]
}
END {
    for (k in words)
        if (words[k])
            print words[k]
        else
            print k
}
$ awk -f script.awk file1.txt file2.txt
wor
fa-re
text
wo-ded
uncial
word-ed
word

击穿

!($1 in words) {
    ...
}

如果第一个字段尚未作为数组words中的键驻留,则仅处理该行。

split($1, f, "-")

使用f作为分隔符,将第一个字段拆分为数组-。该单词的第一部分和第二部分分别位于f[1]f[2]。如果单词未被删减,则它将完整地驻留在f[1]内。

w = f[1] f[2]

通过连接单词的第一部分和第二部分,将dehyphened单词指定给w。如果该单词最初未被删除,则结果将是相同的,因为f[2]为空。

if (f[2])
    words[w] = $1
else
    words[w]

将dehyphened字存储为words数组中的键。如果单词是连字符(f[2]不为空),请将其存储为键的值。

END {
    for (k in words)
        if (words[k])
            print words[k]
        else
            print k
}

处理完文件后,遍历words数组,如果键中包含一个值(带阴影的单词),则打印出来,否则打印出密钥(未加密的单词)。

答案 2 :(得分:1)

这不完全是您所要求的,但可能更符合您的需求。

awk '{k=$1; gsub("-","",k); w[k]=$1 FS w[k]} END{for( i in w) print w[i]}'

这将按等价类对文件中的所有单词进行分组(匹配不带连字符)。你可以从这个结果中获得另一个传球来获得你想要的东西。

uncial
word
woded wo-ded 
wor wor
worded word-ed
text
fa-re fare

优点不是手动检查是否有其他带连字符的单词,并查看每个单词有多少个不同的实例。 例如,这会将之前的列表过滤掉所需的输出。

awk '{w=$1; for(i=1;i<=NF;i++) if(match($i,/-/)!=0)w=$i; print w}'