在awk或sed中匹配具有重复ID的两个文件

在awk或sed中匹配具有重复ID的两个文件,awk,Awk,我有两个文件。文件1有3000行(1500个ID),文件2有1400行(700个ID)。文件1包含文件2中存在的所有ID。我必须匹配File1和file2的ID列,同时保持ID的顺序。如果文件2中的id存在于文件1中,则比较第2列并打印匹配或不匹配。问题是有重复的ID,我需要保留它们。正在寻找awk或sed解决方案。谢谢 File1 ID A 1 13 1 14 2 13 2 13 3 13 3 12 4 13 4 14 5 14 5 14 File

我有两个文件。文件1有3000行(1500个ID),文件2有1400行(700个ID)。文件1包含文件2中存在的所有ID。我必须匹配File1和file2的ID列,同时保持ID的顺序。如果文件2中的id存在于文件1中,则比较第2列并打印匹配或不匹配。问题是有重复的ID,我需要保留它们。正在寻找awk或sed解决方案。谢谢

File1
ID  A
1   13
1   14
2   13
2   13
3   13
3   12
4   13
4   14
5   14
5   14

File 2
ID A
2 13
2 13    
3 13
3 3
5 14
5 15



Desired output
ID A
2 13 Match
2 13 Match    
3 13 Match
3 3 mismatch
5 14 Match
5 15 mismatch

最简单的方法是遍历文件2中的行,并在文件1中为每一行找到匹配的ID。由于您不提供编程语言,以下是伪代码解决方案:

for all rows in file2
  for all rows in file1
    if current_row_file1.id = current_row_file2.id
    then
      if current_row_file1.value_column2 = current_row_file2.value_column2
      then
        print current_row_file2.id + current_row_file2.value_column2 + "Match"
      else
        print current_row_file2.id + current_row_file2.value_column2 + "Mismatch

当您针对文件2中的每一行遍历文件1中的所有记录时,上面的代码需要一些时间。如果文件1中的ID已排序,则可以使用类似二进制搜索的算法来加快处理速度。在这里查找解释

最简单的方法是遍历文件2中的行,并在文件1中为每一行找到匹配的ID。由于您不提供编程语言,以下是伪代码解决方案:

for all rows in file2
  for all rows in file1
    if current_row_file1.id = current_row_file2.id
    then
      if current_row_file1.value_column2 = current_row_file2.value_column2
      then
        print current_row_file2.id + current_row_file2.value_column2 + "Match"
      else
        print current_row_file2.id + current_row_file2.value_column2 + "Mismatch

当您针对文件2中的每一行遍历文件1中的所有记录时,上面的代码需要一些时间。如果文件1中的ID已排序,则可以使用类似二进制搜索的算法来加快处理速度。请在此处查找解释

您可以使用
awk
来实现这一点

awk '
  NR==FNR{ if(a[$1]=="") a[$1]=$2; next}
  /[0-9]/{
    if(a[$1]==$2){
      print $0,"match"
    } else {
      print $0,"mismatch"
    } id=$1
}' File1 File2
输出:

2 13 match
2 13 match
3 13 match
3 3 mismatch
5 14 match
5 15 mismatch
简要说明

  • NR==FNR{…}
    :在文件1中,如果id以前从未显示过,则将id/值保存到数组
    a
  • 如果(a[$1]==2)
    :如果id和值在文件2中匹配,则将记录视为匹配,否则视为不匹配

  • 您可以使用
    awk
    来实现这一点

    awk '
      NR==FNR{ if(a[$1]=="") a[$1]=$2; next}
      /[0-9]/{
        if(a[$1]==$2){
          print $0,"match"
        } else {
          print $0,"mismatch"
        } id=$1
    }' File1 File2
    
    输出:

    2 13 match
    2 13 match
    3 13 match
    3 3 mismatch
    5 14 match
    5 15 mismatch
    
    简要说明

  • NR==FNR{…}
    :在文件1中,如果id以前从未显示过,则将id/值保存到数组
    a
  • 如果(a[$1]==2)
    :如果id和值在文件2中匹配,则将记录视为匹配,否则视为不匹配

  • 为什么输出中显示了
    5 14不匹配
    5 14’确实出现在文件1中的文件1中,第一次出现5的值为14,而文件2中第一次出现5的值不是14(它是15),因此不匹配。因此,文件1中第一次出现的id将与文件2中第一次出现的相同id匹配,文件1中第二次出现的id将与文件2中第二次出现的id匹配。发布的答案是否满足您的要求。您应该在这里给出一些反馈。为什么输出中显示
    5 14不匹配
    5 14’确实出现在文件1中的文件1中,第一次出现5的值为14,而文件2中第一次出现5的值不是14(它是15),因此不匹配。因此,文件1中第一次出现的id将与文件2中第一次出现的相同id匹配,文件1中第二次出现的id将与文件2中第二次出现的id匹配。发布的答案是否满足您的要求。你应该给我一些反馈。我是作为我的老师运行的。awk文件1文件2,但它保持运行,不提供任何output@akang,答案应该很好,我在这里试过了,没有问题。你可以去检查你的脚本,如果它有一些问题。谢谢我得到它运行!但是if语句if(id!=$1&&a[$1]==2)有一些问题。它在某些地方显示“不匹配”,即使在有匹配的地方也是如此。@akang您可以将案例显示出来,或者在问题中修改它,以便我可以获得更多信息。基本上,如果有两个连续的匹配,它会将其中一个显示为不匹配。我以sh的身份运行它。awk文件1文件2,但它保持运行,不提供任何output@akang,答案应该很好,我在这里试过了,没有问题。你可以去检查你的脚本,如果它有一些问题。谢谢我得到它运行!但是if语句if(id!=$1&&a[$1]==2)有一些问题。它在某些地方显示“不匹配”,即使在有匹配的地方也是如此。@akang您可以将案例显示出来,或者在问题中修改它,以便我可以获得更多信息。基本上,如果有两个连续的匹配,它会将一个显示为不匹配。