> For the complete documentation index, see [llms.txt](https://man.bsdcn.org/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://man.bsdcn.org/man1/sort.1.md).

# sort(1)

`sort` — 对文本和二进制文件的记录（行）进行排序或合并

## 名称

`sort`

## 概要

`sort [-bcCdfghiRMmnrsuVz] [-k field1[,field2]] [-S memsize] [-T dir] [-t char] [-o output] [file ...]`

`sort --help`

`sort --version`

## 描述

`sort` 工具按行对文本和二进制文件进行排序。行是以换行符（默认）或 NUL `'\0'` 字符（`-z` 选项）与后续记录分隔的记录。记录可包含任何可打印或不可打印字符。比较基于从每行输入中提取的一个或多个排序键，按照当前 locale 的排序规则和可调整实际排序行为的指定命令行选项，按词典序进行。默认情况下，若未给出键，`sort` 使用整行进行比较。

命令行选项如下：

**`-c`**, **`--check`**, **`-C`**, **`--check=silent|quiet`** 检查单个输入文件是否已排序。若文件未排序，`sort` 产生相应的错误消息并以退出码 1 退出，否则返回 0。若指定了 `-C` 或 `--check=silent`，`sort` 不产生输出。这是 `-c` 的“静默”版本。

**`-m`**, **`--merge`** 仅合并。假定输入文件已经预排序。若它们未排序，输出顺序未定义。

**`-o`** `output`, **`--output`**=`output` 将输出打印到 `output` 文件而非标准输出。

**`-S`** `size`, **`--buffer-size`**=`size` 使用 `size` 作为内存缓冲区的最大大小。可使用大小修饰符 %、b、K、M、G、T、P、E、Z、Y。若未显式指定内存限制，`sort` 最多占用约 90% 的可用内存。若文件太大无法装入内存缓冲区，则使用临时磁盘文件执行排序。

**`-T`** `dir`, **`--temporary-directory`**=`dir` 将临时文件存储在目录 `dir` 中。默认路径为环境变量 `TMPDIR` 的值，若 `TMPDIR` 未定义，则使用 **/var/tmp**。

**`-u`**, **`--unique`** 唯一键。抑制所有键与已处理行相等的行。此选项类似于 `-s`，意味着稳定排序。若与 `-c` 或 `-C` 一起使用，`sort` 还会检查没有重复键的行。

**`-s`** 稳定排序。此选项维持具有相等键的记录的原始顺序。这是一个非标准功能，但被广泛接受和使用。

**`--version`** 打印版本号并静默退出。

**`--help`** 打印帮助文本并静默退出。

以下选项覆盖默认排序规则。当排序选项独立于键字段规范出现时，它们全局应用于所有排序键。当附加到特定键（参见 `-k`）时，排序选项覆盖其所附加键的所有全局排序选项。

**`-b`**, **`--ignore-leading-blanks`** 比较行时忽略前导空白字符。

**`-d`**, **`--dictionary-order`** 比较时仅考虑空格和字母数字字符。

**`-f`**, **`--ignore-case`** 比较前将所有小写字符转换为大写等效字符，即执行不区分大小写的排序。

**`-g`**, **`--general-numeric-sort`**, **`--sort=general-numeric`** 按一般数值排序。与 `-n` 不同，此选项处理一般浮点数。它允许的格式比 `-n` 更宽松，但性能有明显缺点。

**`-h`**, **`--human-numeric-sort`**, **`--sort=human-numeric`** 按数值排序，但会考虑 SI 后缀（如有）。首先按数字符号（负、零或正）排序；然后按 SI 后缀（空、`k` 或 `K`，或 `MGTPEZY` 之一，按此顺序）排序；最后按数值排序。SI 后缀必须紧跟数字。例如，'12345K' 排在 '1M' 之前，因为 M 比 K“更大”。此排序选项适用于对带 `-h` 或 `-H` 选项（人类可读）的单次 `df` 命令输出进行排序。

**`-i`**, **`--ignore-nonprinting`** 忽略所有不可打印字符。

**`-M`**, **`--month-sort`**, **`--sort=month`** 按月份排序。未知字符串被视为小于月份名称。

**`-n`**, **`--numeric-sort`**, **`--sort=numeric`** 按算术值对字段进行数值排序。字段开头可有可选空格、可选减号、零个或多个数字（包括小数点和可能的千位分隔符）。

**`-R`**, **`--random-sort`**, **`--sort=random`** 按随机顺序排序。这是输入的随机排列，但相等键排在一起。它通过对输入键哈希并对哈希值排序实现。哈希函数随机选择。哈希函数由 **/dev/random** 内容随机化，或由 `--random-source` 指定的文件内容随机化。即使指定了多个排序字段，所有字段都使用相同的随机哈希函数。

**`-r`**, **`--reverse`** 以相反顺序排序。

**`-V`**, **`--version-sort`** 对版本号排序。输入行被视为形式为 PREFIX VERSION SUFFIX 的文件名，其中 SUFFIX 匹配正则表达式 "(.(\[A-Za-z\~]\[A-Za-z0-9\~]*)?)*"。文件按其前缀和版本进行比较（版本号中的前导零被忽略，参见下例）。若输入字符串不匹配该模式，则使用字节比较函数进行比较。所有字符串比较在 C locale 中执行，忽略 locale 环境设置。

**示例：**

```sh
$ ls sort* | sort -V
sort-1.022.tgz
sort-1.23.tgz
sort-1.23.1.tgz
sort-1.024.tgz
sort-1.024.003.
sort-1.024.003.tgz
sort-1.024.07.tgz
sort-1.024.009.tgz
```

字段分隔符的处理可通过以下选项改变：

**`-b`**, **`--ignore-leading-blanks`** 确定受限排序键的起始和结束位置时忽略前导空格（参见 `-k`）。若 `-b` 在第一个 `-k` 选项之前指定，它全局应用于所有键规范。否则，`-b` 可独立附加到键规范的每个 `field` 参数。`-b`。

**`-k`** `field1`\[,`field2`], **`--key`**=`field1`\[,`field2`] 定义一个受限排序键，起始位置为 `field1`，可选结束位置为 `field2`。`-k` 选项可多次指定，后续键在先前键比较相等时进行比较。`-k` 选项替代了过时的 `+pos1` 和 `-pos2` 选项，但旧记法仍受支持。

**`-t`** `char`, **`--field-separator`**=`char` 使用 `char` 作为字段分隔符。确定键偏移时，初始 `char` 不视为字段的一部分。`char` 的每次出现都是有意义的（例如，“`charchar`”分隔出一个空字段）。若未指定 `-t`，默认字段分隔符是空白字符序列，连续空白 *不* 分隔空字段，但确定键偏移时初始空白 *会* 被视为字段的一部分。要使用 NUL 作为字段分隔符，使用 `-t` `'\0'`。

**`-z`**, **`--zero-terminated`** 使用 NUL 作为记录分隔符。默认情况下，文件中的记录以换行符分隔。使用此选项时，NUL（`'\0'`）用作记录分隔符。

其他选项：

**`--batch-size`**=`num` 指定 `sort` 可同时打开的最大文件数。此选项在有许多输入文件或使用临时文件时影响行为。默认值为 16。

**`--compress-program`**=`PROGRAM` 使用 PROGRAM 压缩临时文件。PROGRAM 在无参数调用时必须将标准输入压缩到标准输出。以参数 `-d` 调用时必须将标准输入解压到标准输出。若 PROGRAM 失败，`sort` 必须以错误退出。可在此处使用的 PROGRAM 示例为 bzip2。

**`--random-source`**=`filename` 在随机排序中，文件内容用作哈希函数选择的“种子”数据源。两次使用相同种子数据的随机排序将使用相同的哈希函数，若输入也相同则产生相同结果。默认使用文件 **/dev/random**。

**`--debug`** 向标准输出打印一些关于排序过程的额外信息。

**`--parallel`** 设置最大执行线程数。默认数量等于 CPU 数量。

**`--files0-from`**=`filename` 从文件 `filename` 中获取输入文件列表。文件名必须以 NUL 分隔（类似于命令“find ... -print0”产生的输出）。

**`--radixsort`** 若排序规范允许，尝试使用基数排序。基数排序仅可用于简单 locale（C 和 POSIX），且不能用于数值或月份排序。基数排序非常快速且稳定。

**`--mergesort`** 使用归并排序。这是一种通用算法，始终可使用，但并不总是最快的。

**`--qsort`** 若排序规范允许，尝试使用快速排序。此排序算法不能与 `-u` 和 `-s` 一起使用。

**`--heapsort`** 若排序规范允许，尝试使用堆排序。此排序算法不能与 `-u` 和 `-s` 一起使用。

**`--mmap`** 尝试使用文件内存映射系统调用。在某些情况下可能提高速度。

可用操作数如下：

**`file`** 待排序、合并或检查的文件路径名。若未指定 `file` 操作数，或 `file` 操作数为 `-`，则使用标准输入。

字段定义为字段分隔符和记录分隔符（默认为换行符）以外字符的最大序列。除非指定了 `-b`，否则前导空格包含在字段中；空白字符序列的第一个空格作为字段分隔符并包含在字段中（除非指定了 `-t`）。例如，行首的所有空格都被视为第一个字段的一部分。

字段通过 `-k` `field1`\[,`field2`] 命令行选项指定。若缺少 `field2`，键的结束默认为行尾。

参数 `field1` 和 `field2` 的形式为 *m.n*（*m,n* > 0），后可跟一个或多个修饰符 `b`、`d`、`f`、`i`、`n`、`g`、`M` 和 `r`，对应上述讨论的选项。指定 `b` 时仅应用于其所在的 `field1` 或 `field2`，而其余修饰符无论仅与 `field1` 或 `field2` 一起指定还是与两者一起指定，都应用于整个键字段。以 *m.n* 指定的 `field1` 位置解释为第 *m* 个字段开头起第 *n* 个字符。`field1` 中缺少 *.n* 意味着 *.1*，表示第 *m* 个字段的第一个字符；若 `-b` 选项生效，*n* 从第 *m* 个字段的第一个非空格字符起计数；*m*.1b 指第 *m* 个字段的第一个非空格字符。1.*n* 指行首起第 *n* 个字符；若 *n* 大于行长度，该字段视为空。

*n* 个位置始终从字段开头计数，即使字段短于指定位置数。因此，键实际上可从后续字段中的某个位置开始。

以 *m.n* 指定的 `field2` 位置解释为第 *m* 个字段开头起（含分隔符）第 *n* 个字符。缺少 *.n* 表示第 *m* 个字段的最后一个字符；*m* = 0 表示行尾。因此选项 `-k` `v.x,w.y` 与过时选项 `+v-1.x-1` `-w-1.y` 同义；省略 *y* 时，`-k` `v.x,w` 与 `+v-1.x-1` `-w.0` 同义。过时的 `+pos1` `-pos2` 选项仍受支持，但 `-w.0b` 除外，它没有 `-k` 等价项。

## 环境变量

**`LC_COLLATE`** 用于确定记录排序整理规则的 locale 设置。

**`LC_CTYPE`** 用于字符大小写转换和分类的 locale 设置，即哪些字符被视为空格等。

**`LC_MESSAGES`** 确定 `sort` 输出消息语言的 locale 设置。

**`LC_NUMERIC`** 确定数值排序中使用数字格式的 locale 设置。

**`LC_TIME`** 确定月份排序中使用月份格式的 locale 设置。

**`LC_ALL`** 覆盖上述所有 locale 设置的 locale 设置。此环境变量可一次性将所有这些设置为相同值。

**`LANG`** 若既未设置相应环境变量也未设置 `LC_ALL`，作为最后手段用于确定各种特定于 locale 的行为。

**`TMPDIR`** 存储临时文件的目录路径。注意 `TMPDIR` 可被 `-T` 选项覆盖。

**`GNUSORT_NUMERIC_COMPATIBILITY`** 若已定义，`-t` 不会覆盖 locale 数字符号，即千位分隔符和小数分隔符。默认情况下，若指定的 `-t` 与千位分隔符或小数点相同，该符号将被视为字段分隔符。旧行为不太明确；该符号同时被视为字段分隔符和数字分隔符。此环境变量启用旧行为。

## 文件

**`/var/tmp/.bsdsort.PID.*`** 临时文件。

**`/dev/random`** 随机排序的默认种子文件。

## 退出状态

`sort` 工具应以以下值之一退出：

**0** 成功排序输入文件，或与 `-c` 或 `-C` 一起使用时，输入文件已满足排序条件。

**1** 使用 `-c` 或 `-C` 选项时发现乱序（或非唯一）。

**2** 发生错误。

## 参见

[comm(1)](/man1/comm.1.md), join(1), [uniq(1)](/man1/uniq.1.md)

## 标准

`sort` 工具遵循 IEEE Std 1003.1-2008（“POSIX.1”）规范。

标志 \[`-ghRMSsTVz`] 是 POSIX 规范的扩展。

所有长选项都是规范的扩展，其中一些为兼容 GNU 版本而提供，另一些为自有扩展。

旧键记法 `+pos1` 和 `-pos2` 来自 `sort` 的旧版本，仍受支持，但强烈建议不要使用。

## 历史

`sort` 命令首次出现在 Version 1 AT\&T UNIX 中。

## 作者

Gabor Kovesdan <gabor@FreeBSD.org>,

Oleg Moskalenko <mom040267@gmail.com>

## 注释

此 `sort` 实现对输入行长度（除可用内存限制外）或行内允许的字节没有限制。

性能很大程度上取决于 locale 设置、排序键的高效选择和键复杂性。最快的排序是使用 C locale、整行、带 `-s` 选项。一般而言，C locale 最快，其次是单字节 locale，多字节 locale 最慢，但始终遵循正确的整理顺序。至于键规范，行处理越简单，搜索越快。

按算术值排序时，使用 `-n` 比使用 `-g` 性能好得多，因此建议尽可能使用 `-n`。
