【问题标题】:Removing specific lines/rows or duplicates from a file in Linux从 Linux 中的文件中删除特定的行/行或重复项
【发布时间】:2020-10-23 09:29:07
【问题描述】:

我想在 Linux 上使用特定变量“SAMPLE”下的值从 .csv 文件(名为“mydata”)中删除特定行。实际上,我的文件中有 250 个重复项,原始文件有 15000 行和 66 列,我想删除每个重复项的一份副本并保留一份。如果您查看其他变量,例如“ID”,您会看到重复项。因此,如果我可以根据“SAMPLE”列中的值删除重复项或特定行,任何解决方案都对我有用。 SAMPLE 是我的数据中唯一重复名称不同的列。我的数据是这样的;

 ID      SAMPLE LABNO Oth_ID sex   age   bmi ca_1 pd_7
1003341  21863 21863     NA   1 48.68 22.42    0    0
1003343  22697 22697     NA   1 48.98 23.25    0    0
1003347   4421  4421     NA   1 48.70 25.56   NA   NA
1003348   1642  1642     NA   1 48.72 16.57   NA   NA
1003349   4163  4163   6069   1 49.02 23.47    1   NA
1003349   6069  4163   6069   1 49.02 23.47    1   NA
1003356   5347  9053   5347   1 49.08 24.81    0    0
1003356   9053  9053   5347   1 49.08 24.81    0    0
1003357    695   695     NA   1 49.08 22.32   NA   NA
1003360  19833 19833     NA   1 48.55 22.48    0    0
1003365   5392  6843   5392   1 48.70 23.08    0    0
1003365   6843  6843   5392   1 48.70 23.08    0    0

【问题讨论】:

    标签: csv duplicates rows


    【解决方案1】:

    @zinovyev 的代码对我来说很好用。 @Tabbi,要解决您的问题,请运行下面的 remove_dup.sh 脚本(代码+数据在一个文件中):

    #!/bin/bash
    
    # Write the top line
    sed '0,/^__DATA__$/d' "$0" | head -n 1
    
    # Make unique, sort and append other lines
    sed '0,/^__DATA__$/d' "$0" | tail -n +2 | sort -k 3,4 -u | sort -V
    
    exit
    
    __DATA__
     ID      SAMPLE LABNO Oth_ID sex   age   bmi ca_1 pd_7
    1003341  21863 21863     NA   1 48.68 22.42    0    0
    1003343  22697 22697     NA   1 48.98 23.25    0    0
    1003347   4421  4421     NA   1 48.70 25.56   NA   NA
    1003348   1642  1642     NA   1 48.72 16.57   NA   NA
    1003349   4163  4163   6069   1 49.02 23.47    1   NA
    1003349   6069  4163   6069   1 49.02 23.47    1   NA
    1003356   5347  9053   5347   1 49.08 24.81    0    0
    1003356   9053  9053   5347   1 49.08 24.81    0    0
    1003357    695   695     NA   1 49.08 22.32   NA   NA
    1003360  19833 19833     NA   1 48.55 22.48    0    0
    1003365   5392  6843   5392   1 48.70 23.08    0    0
    1003365   6843  6843   5392   1 48.70 23.08    0    0
    

    你应该会看到结果

     ID      SAMPLE LABNO Oth_ID sex   age   bmi ca_1 pd_7
    1003341  21863 21863     NA   1 48.68 22.42    0    0
    1003343  22697 22697     NA   1 48.98 23.25    0    0
    1003347   4421  4421     NA   1 48.70 25.56   NA   NA
    1003348   1642  1642     NA   1 48.72 16.57   NA   NA
    1003349   4163  4163   6069   1 49.02 23.47    1   NA
    1003356   5347  9053   5347   1 49.08 24.81    0    0
    1003357    695   695     NA   1 49.08 22.32   NA   NA
    1003360  19833 19833     NA   1 48.55 22.48    0    0
    1003365   5392  6843   5392   1 48.70 23.08    0    0
    

    【讨论】:

      【解决方案2】:

      您可以使用简单的sort 命令。只需使用 -k 键定义正确的列并添加 -u 选项以使结果集唯一:

      sort -k 3,4 -u < mydata.csv
      

      在此答案中,我假设您正在寻找基于 LABNOOth_ID 列的唯一值,即数字 34

      其实是把列名放在首位使用:

      # Write the top line to the new file
      head -n 1 mydata.csv > mydata.uniq.csv
      
      # Make unique, sort and append other lines
      tail -n +2 mydata.csv | sort -k 3,4 -u | sort -V >> mydata.uniq.csv
      

      之前

       ID      SAMPLE LABNO Oth_ID sex   age   bmi ca_1 pd_7
      1003341  21863 21863     NA   1 48.68 22.42    0    0
      1003343  22697 22697     NA   1 48.98 23.25    0    0
      1003347   4421  4421     NA   1 48.70 25.56   NA   NA
      1003348   1642  1642     NA   1 48.72 16.57   NA   NA
      1003349   4163  4163   6069   1 49.02 23.47    1   NA
      1003349   6069  4163   6069   1 49.02 23.47    1   NA
      1003356   5347  9053   5347   1 49.08 24.81    0    0
      1003356   9053  9053   5347   1 49.08 24.81    0    0
      1003357    695   695     NA   1 49.08 22.32   NA   NA
      1003360  19833 19833     NA   1 48.55 22.48    0    0
      1003365   5392  6843   5392   1 48.70 23.08    0    0
      1003365   6843  6843   5392   1 48.70 23.08    0    0
      

      之后:

       ID      SAMPLE LABNO Oth_ID sex   age   bmi ca_1 pd_7
      1003341  21863 21863     NA   1 48.68 22.42    0    0
      1003343  22697 22697     NA   1 48.98 23.25    0    0
      1003347   4421  4421     NA   1 48.70 25.56   NA   NA
      1003348   1642  1642     NA   1 48.72 16.57   NA   NA
      1003349   4163  4163   6069   1 49.02 23.47    1   NA
      1003356   5347  9053   5347   1 49.08 24.81    0    0
      1003357    695   695     NA   1 49.08 22.32   NA   NA
      1003360  19833 19833     NA   1 48.55 22.48    0    0
      1003365   5392  6843   5392   1 48.70 23.08    0    0
      

      【讨论】:

      • @andreoss 实际上,SMAPLE 列是我文件中的第 2 列,它是唯一具有唯一值的列。由于“mydata”是两个文件的组合,因此它具有相同主题的重复项,具有不同的 SMAPLE 编号。如果您查看 LABNO 和 OthID 列,您会看到重复项。我的主要目标是从文件中删除这些重复项。请忽略我的问题中示例数据中的第一列,我现在已编辑删除此列。
      • @Tabbi 我已经根据您的评论更新了答案。实际上SAMPLE 列最初的编号为3,因为列是根据空格分隔符计算的(因为我们没有设置要使用的其他分隔符),列号1 是带有数字的列.希望它现在能满足您的需求;)
      • 当我运行你提到的命令时,我最终在输出文件'mydata.uniq.csv'ID,SAMPLE,LABNO,Oth_ID,sex,age,bmi,ca_1,pd_7 1003341,21863,21863,,1,48.68,22.42,0,0 中只有一行。只有这个......我做错了什么吗?
      • @Tabbi 好像出了点问题。你运行这两个命令吗?您能否提供以下输出:cat mydata.csv | sed -n '1d;p' mydata.csv | sort -k 3,4 -u | sort -V
      • 是的,我从头到尾运行了您答案中的所有命令(排序、头部和 sed)。你给出的 cat 命令的输出是这样的; 1003341,21863,21863,,1,48.68,22.42,0,0
      猜你喜欢
      • 2016-08-13
      • 1970-01-01
      • 2015-04-24
      • 2018-06-16
      • 1970-01-01
      • 2014-06-03
      • 2021-12-16
      相关资源
      最近更新 更多