用sort对文件排序,发现这个命令比想象中要复杂和强大,仔细研究了一下文档,记录一下。
首先看一下文档,建议浏览一下,用的时候再详细看看:
$ sort --help
用法:sort [选项]... [文件]...
或:sort [选项]... --files0-from=F
Write sorted concatenation of all FILE(s) to standard output.
如果没有指定文件,或者文件为"-",则从标准输入读取。
必选参数对长短选项同时适用。
排序选项:
-b, --ignore-leading-blanks 忽略前导的空白区域
-d, --dictionary-order 只考虑空白区域和字母字符
-f, --ignore-case 忽略字母大小写
-g, --general-numeric-sort compare according to general numerical value
-i, --ignore-nonprinting consider only printable characters
-M, --month-sort compare (unknown) < 'JAN' < ... < 'DEC'
-h, --human-numeric-sort 使用易读性数字(例如: 2K 1G)
-n, --numeric-sort compare according to string numerical value
-R, --random-sort shuffle, but group identical keys. See shuf(1)
--random-source=FILE get random bytes from FILE
-r, --reverse reverse the result of comparisons
--sort=WORD 按照WORD 指定的格式排序:
一般数字-g,高可读性-h,月份-M,数字-n,
随机-R,版本-V
-V, --version-sort 在文本内进行自然版本排序
其他选项:
--batch-size=NMERGE 一次最多合并NMERGE 个输入;如果输入更多
则使用临时文件
-c, --check, --check=diagnose-first 检查输入是否已排序,若已有序则不进行操作
-C, --check=quiet, --check=silent 类似-c,但不报告第一个无序行
--compress-program=程序 使用指定程序压缩临时文件;使用该程序
的-d 参数解压缩文件
--debug 为用于排序的行添加注释,并将有可能有问题的
用法输出到标准错误输出
--files0-from=文件 从指定文件读取以NUL 终止的名称,如果该文件被
指定为"-"则从标准输入读文件名
-k, --key=KEYDEF sort via a key; KEYDEF gives location and type
-m, --merge merge already sorted files; do not sort
-o, --output=文件 将结果写入到文件而非标准输出
-s, --stable 禁用last-resort 比较以稳定比较算法
-S, --buffer-size=大小 指定主内存缓存大小
-t, --field-separator=分隔符 使用指定的分隔符代替非空格到空格的转换
-T, --temporary-directory=目录 使用指定目录而非$TMPDIR 或/tmp 作为
临时目录,可用多个选项指定多个目录
--parallel=N 将同时运行的排序数改变为N
-u, --unique 配合-c,严格校验排序;不配合-c,则只输出一次排序结果
-z, --zero-terminated line delimiter is NUL, not newline
--help 显示此帮助信息并退出
--version 显示版本信息并退出
KEYDEF is F[.C][OPTS][,F[.C][OPTS]] for start and stop position, where F is a
field number and C a character position in the field; both are origin 1, and
the stop position defaults to the line's end. If neither -t nor -b is in
effect, characters in a field are counted from the beginning of the preceding
whitespace. OPTS is one or more single-letter ordering options [bdfgiMhnRrV],
which override global ordering options for that key. If no key is given, use
the entire line as the key. Use --debug to diagnose incorrect key usage.
SIZE may be followed by the following multiplicative suffixes:
% 1% of memory, b 1, K 1024 (default), and so on for M, G, T, P, E, Z, Y.
*** WARNING ***
The locale specified by the environment affects sort order.
Set LC_ALL=C to get the traditional sort order that uses
native byte values.
GNU coreutils online help: <http://www.gnu.org/software/coreutils/>
请向<http://translationproject.org/team/zh_CN.html> 报告sort 的翻译错误
Full documentation at: <http://www.gnu.org/software/coreutils/sort>
or available locally via: info '(coreutils) sort invocation'
它的最基本用法就是”sort -k2,2 file”,表示排序的key开始列是2,结束列是2,也就是按照第二列排序。
下面通过一个例子来逐步了解更加复杂的用法。假设我们要排序的文件为:
$ cat st
abc 100 90
ddd 100 80
fff 80 100
eee 120 80
xxx 100 100
假设我们希望按照第二列排序:
$ sort -k 2,2 st
abc 100 90
ddd 100 80
xxx 100 100
eee 120 80
fff 80 100
好像不对?因为默认是用字符串来排序的,因此80排在了100后面,因此我们需要加入-n或者-g。-n是parse普通的数字,比如”1.23”,但是它不能parse科学计数法的数字比如”2e-30”,而-g可以parse。
$ sort -n -k 2,2 st
fff 80 100
abc 100 90
ddd 100 80
xxx 100 100
eee 120 80
接下来我们可能想实现这样的排序:先按第二列排序,如果第二列相同再按第三列排序。我们可能会这样:
$ sort -n -k 2,3 st
fff 80 100
abc 100 90
ddd 100 80
xxx 100 100
eee 120 80
很遗憾,-k2,3的意思是把第二列和第三列放到一起排序,但是两个数字是无法放到一起的。如果我们把它成字符串则是可以拼起来的:
$ sort -k 2,3 st
xxx 100 100
ddd 100 80
abc 100 90
eee 120 80
fff 80 100
上面的命令会把第二列和第三列的字符串拼起来,因此”100 100”会变成”100100”,但这不是我们想要的。
为了实现我们的目的,我们可以使用多个-k。
$ sort -n -k 2,2 -k 3,3 st
fff 80 100
ddd 100 80
abc 100 90
xxx 100 100
eee 120 80
我们看到第二列为100的3行果然是按照第三列排序了。接下来我们希望按照降序排列,那么可以使用-r:
$ sort -r -n -k 2,2 -k 3,3 st
eee 120 80
xxx 100 100
abc 100 90
ddd 100 80
fff 80 100
一切如我们所愿,但是如果我们想第二列降序但是第三列升序呢?这是-r就必须放到-k里,表示只对这个key有效:
$ sort -n -k 2,2r -k 3,3 st
fff 80 100
eee 120 80
ddd 100 80
abc 100 90
xxx 100 100
我们甚至可以把第二列的key看成数值但是把第三列看成字符串:
$ sort -k 2,2nr -k 3,3 st
eee 120 80
xxx 100 100
ddd 100 80
abc 100 90
fff 80 100
上面的命令把第二列当成数值,然后逆序排列;而第三行当成字符串正序排列。
- 显示Disqus评论(需要科学上网)