bash - 加入给出警告 "file1 is not in sorted order"

标签 bash unix

正在测试新版 bash 4.1.2(1)-release 中的旧脚本 ,并在控制台中遇到此警告:

join: file 1 is not in sorted order
join: file 2 is not in sorted order

我很确定这两个文件都已排序。文件实际上已正确合并。

下面是脚本:

cat $FILE1_PATH'.processed.1' | cut -d'|' -f4,8 | sort | uniq -u  > $FILE1_PATH.'processed.2'
cat $FILE2_PATH'.processed.1' | cut -d'|' -f1,8 | sort | uniq -u > $FILE2_PATH.'processed.2'
join -t$'|' -1 1 -2 1 $FILE1_PATH.'processed.2' $FILE2_PATH.'processed.2' > $MERGEFILE_PATH

这个脚本的工作:

  1. 从文件 1 中提取字段 4 和 8
  2. 从文件 2 中提取字段 1 和 8
  3. 使用连接键 file1.field4 = file2.field1 组合提取的字段
  4. 删除所有重复项。

FILE1.processed.2:

21VIANET GP INC|GOV
ABN|ABN1
ABN|ABN2
ABOC|ABOC1
ABOC|ABOC1
ABOC|ABOC2
....

FILE2.processed.2:

ABN|Banks
ABOC|Pharmaceuticals
GOV|Government Agency 
....

输出:

GOV|21VIANET GP INC|Government Agency
ABN|ABN1|Banks
ABN|ABN2|Banks
ABOC|ABOC1|Pharmaceuticals
ABOC|ABOC2|Pharmaceuticals  
....

在 bash 版本 3.2.25(1)-release 中运行相同的脚本不会发出警告。有解决警告的想法吗?

更新: 似乎原因是由输入文件中的这些行引起的......

ADBC|Banks 
ADB|Banks

Join 期望 ADBC 位于 ADB 之后,如下所示:

ADB|Banks
ADBC|Banks

但是我尝试将排序脚本从 sort -u 更改为 sort -t$'|' -k1(根据第一个字段排序)但仍然无法正常工作......

最佳答案

join 手册页中的建议是在加入字段 1 时使用 sort -k 1b,1。(它说“当加入没有选项”,但就字段选择而言,您的连接相当于没有选项。-1 1-2 1 是默认值。)您可以添加 -t '|' ,它将完美匹配您的 join

-k1 表示从 1 到结尾的所有字段。 -k1,1 仅表示字段 1。如果您有前导空格并想忽略它,则 b 是必需的。排序语法很奇怪。这是 POSIX 重新设计它以使其变得合理之后。如果您曾经编写过看起来并不复杂的排序命令,那么它可能没有按照您的意愿行事。

--debug 添加到您的排序命令以查看它用作键的内容。使用包含这些行的示例文件:

ADBC|Banks
ADB|Banks
 ADBC|Banks

可以看到各种-k选项的效果:

$ sort -s -t '|' -k 1 --debug file
sort: using simple byte comparison
 ADBC|Banks
___________
ADBC|Banks
__________
ADB|Banks
_________
$ sort -s -t '|' -k 1,1 --debug file
sort: using simple byte comparison
 ADBC|Banks
_____
ADB|Banks
___
ADBC|Banks
____
$ sort -s -t '|' -k 1b,1 --debug file
sort: using simple byte comparison
ADB|Banks
___
ADBC|Banks
____
 ADBC|Banks
 ____

现在您可能想知道我在其中添加的 -s。如果没有它,则将整行作为字符串进行默认的最后比较,这适用于具有相同键的行。这通常不是问题,您可能不需要使用 -s。只是在使用 --debug 时,最后的比较会使列表变得困惑,所以我喜欢使用 -s 来摆脱它。

关于bash - 加入给出警告 "file1 is not in sorted order",我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26626407/

相关文章:

python - BASH 和 Python

c - 是否存在搜索 unix $PATH 变量并在某个文件存在时返回 true 的函数?

控制多个 child ,处理 sigchild

linux - 如何检查LINUX中的日期格式

带有 fswatch 的正则表达式 - 排除不以 ".txt"结尾的文件

c++ - 将 C++ 程序的输出通过管道传递给另一个程序

bash - 如何根据变量的长度来控制线条的长度并且能够使线条均匀

linux - 如何在 Linux 或 R 中检查 CPU 核心使用情况

windows - 文件名通配 Windows 与 Unix

bash - 只打印 grep 匹配本身,既不打印行上的其他内容,也不打印额外的换行符