我对使用 awk/grep 等比较陌生,想过滤一些数据。我有一个大型电子表格,我想逐列显示唯一值。例如我想改变这个:
DS571187 DS571220 DS571200 DS571194
contig1 contig3 contig4 contig7
contig2 contig3 contig4 contig7
contig1 contig4 contig6 contig8
contig1 contig5 contig6 contig9
contig2 contig4 contig6 contig9
contig2
contig2
看起来像这样的东西:
DS571187 DS571220 DS571200 DS571194
contig1 contig3 contig4 contig7
contig2 contig4 contig6 contig8
contig5 contig9
基本上,我试图将每一列作为其自己的列表进行排序,并通过这种方式获取唯一值。任何帮助将不胜感激。
琥珀色
最佳答案
假设您的输入文件看起来是用制表符分隔的:
$ cat tst.awk
BEGIN { FS=OFS="\t" }
{
for (colNr=1;colNr<=NF;colNr++) {
if (!seen[colNr,$colNr]++) {
val[++colRowNr[colNr],colNr] = $colNr
numRows = (colRowNr[colNr] > numRows ? colRowNr[colNr] : numRows)
}
}
numCols = (NF > numCols ? NF : numCols)
}
END {
for (rowNr=1;rowNr<=numRows;rowNr++) {
for (colNr=1;colNr<=numCols;colNr++) {
printf "%s%s", val[rowNr,colNr], (colNr<numCols ? OFS : ORS)
}
}
}
$ awk -f tst.awk file | column -s$'\t' -t
DS571187 DS571220 DS571200 DS571194
contig1 contig3 contig4 contig7
contig2 contig4 contig6 contig8
contig5 contig9
调用 column
只是为了让对齐在网站上看起来漂亮。
如果它不是制表符分隔的,那么为了这个简洁而稳健,你需要 GNU awk for FIELDWIDTHS 来识别中间行中可能为空的字段,就像这个输入(你应该测试其他潜在的解决方案,因为后面的输入列短于我预计较早的那些可能会发生在您的真实数据中,并使这个问题更难解决):
$ column -s$'\t' -t file
DS571187 DS571220 DS571200 DS571194
contig1 contig3 contig4 contig7
contig2 contig3 contig7
contig1 contig4 contig8
contig5 contig9
contig9
$ awk -f tst.awk file | column -s$'\t' -t
DS571187 DS571220 DS571200 DS571194
contig1 contig3 contig4 contig7
contig2 contig4 contig8
contig5 contig9
关于unix - 使用 awk 在每列中显示唯一值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39082214/