对 + 和 - 等特殊字符进行排序

对 + 和 - 等特殊字符进行排序

我有一个由多行和多列组成的文件。列由 \t 分隔。现在我想根据第二列对文件进行排序,这可以通过例如sort -f -t$'\t' -k2 file.txt.但是,第二列包含以下值:+o-。如何对+顶部、o中间和-底部进行排序?

此外,我还有另一列,例如第 5 列,并且希望对该列的文件进行排序。但是,我想指定我个人的顺序,即n在顶部、s在中间、l在底部。

如果有一个程序可以有效地实现我的目标,我会更喜欢该解决方案。否则我正在寻找一个自写的函数。

答案1

有一种技术称为 DSU、装饰-排序-取消装饰或 Schwartzian 变换。

基本方法是发明自己的替代键,它可以是数据的任意组合(从记录的任何部分提取,可能依赖于其他字段)。这些只需按照所需的重要性顺序进行排名即可。例如,零填充数字字段通常很有帮助。您可以通过添加输入行号作为最终子项来使最终顺序稳定。所有记录的总密钥长度必须相同。

然后根据 -k1.1 顺序(整个记录)对它们进行排序。这通常比多键排序更快,因为通常排序会为每次比较重建两个多键。

最后,通过切断固定长度的修饰来取消修饰排序的输出。

答案2

我们仍然可以使用sort,以防它是一个大文件:

#!/usr/bin/env bash

perl -F'\t' -ne '{$F[1] =~ s/o/,/; $F[4] =~ s/l/t/; print join "\t",@F}' file|\
sort -t $'\t' -k 2,2 -k 5,5 |\
perl -F'\t' -ne '{$F[1] =~ s/,/o/; $F[4] =~ s/t/l/; print join "\t",@F}'

第一个 Perl 脚本更改o,第二列、第五lt,以准备排序。

第二个 perl 脚本又变回来了。

相关内容