为什么列命令不能正确对齐列?

为什么列命令不能正确对齐列?

在我问的另一个问题中如何在使用 ls 时隐藏所有 .pyc 文件,伊格纳西奥提出以下建议: ls | grep -v'.pyc$' | 列

正如我上面提到的,这并不能精确地工作,因为输出有时会错位:

ceasarbautista@hse140:~/Desktop/Statistics/statistics/markov$ ls
README          __init__.pyc        markov.py       matrix2graph.pyc    pathfinder.pyc      priority_dict.pyc   spanning.py
__init__.py     graph.py        matrix2graph.py     pathfinder.py       priority_dict.py    space.py        vector.py
ceasarbautista@hse140:~/Desktop/Statistics/statistics/markov$ ls | grep -v '\.pyc$' | column
README      graph.py        matrix2graph.py priority_dict.py    spanning.py
__init__.py markov.py   pathfinder.py   space.py        vector.py

虽然我得到了满意的答案,但我很好奇:为什么列会这样做(并且可以修复它以正确打印)?

答案1

当不带任何选项调用时,column使每个分隔字符串与最近的字符串对齐制表符停止 柱子。在终端中,这通常位于每 8 个字符列上。看一下这个示例:

创建一个文件 ( ztxt) 包含一些标签-特点 \t分隔字符串,分布在 3 行中,以换行符结尾\n

aaa1\taaaaaaaaaaaaaa2\taaaaaaaaaaaaaaaaaaa3\taaa4
bbbbbbb1\tbbb2\tbbb3
ccc1\tccc2

输出:column ztxt- 与最近的完全对齐制表符停止

aaa1    aaaaaaaaaaaaaa2 aaaaaaaaaaaaaaaaaaa3    aaa4
bbbbbb1 bbb2    bbb3
ccc1    ccc2
|       |       |       |       |       |       |
|-------|-------|-------|-------|-------|-------|

要将每个连续字段的 LSH 与其上面的字段对齐,您需要使用以下-t选项,例如:column -t ztxt

aaa1     aaaaaaaaaaaaaa2  aaaaaaaaaaaaaaaaaaa3  aaa4
bbbbbb1  bbb2             bbb3
ccc1     ccc2

如果您的所有数据都在一个长流中,没有任何换行符,您可以使用过滤器引入它们;例如每一个4字段。 sed可以用这个命令来做到。

sed -re 's/(([^\t]*\t){3}[^\t]*)\t/\1\n/g' 

默认情况下,该column命令会将多个相邻分隔符合并为一个分隔符。为了在sed过滤器中满足这一点,它还需要:

sed -re 's/\t+/\t/g;' 

所以分割连续流的命令制表符分隔字符串,因为每第四个字符串是:

<ztxt sed -re 's/\t+/\t/g;s/(([^\t]*\t){3}[^\t]*)\t/\1\n/g' | column -t  

这种连续输入流的输出是(使用原始示例输入,但通过用制表符替换原始换行符进行修改 - 它仍然必须保留其尾随 \n):

aaa1      aaaaaaaaaaaaaa2  aaaaaaaaaaaaaaaaaaa3  aaa4
bbbbbbb1  bbb2             bbb3                  ccc1
ccc2

答案2

对于多个分隔符位。令人烦恼的是 -n 选项仅在 Debian 中可用,它处理多个分隔符。

column -t -n <file>

答案3

要在输出中显示不可打印的字符(尽可能作为 C 转义码),ls您还可以使用命令-b的选项ls

ls -Cb | grep -v '\.pyc$' | column -t

答案4

列的问题是它在 \s+ 上分割,我不知道如何使其在单个选项卡上分割。我编写了这个更灵活的脚本来解决这个问题,任何人都可以免费使用:

http://itmat.greg.s3.amazonaws.com/display.pl.gz

这是完整的用法:

  -------------------------------------------------- ------------------------
 |该脚本在正确对齐的列中显示制表符分隔的文本。 |
 | |
 |用法:perl display.pl [行数] [选项] |
 | |
 |制表符分隔在哪里。 |
 | |
 |如果后面跟一个正整数N,则只有前N行|
 |将被退回。 |
 | |
 |如果行很长,则该脚本通过管道传输到“less -S”效果最佳。 |
 | |
 | [选项] |
 | |
 | -noheader :默认情况下假定有标题行。 |
 | |
 | -nodots :默认情况下,如果列很宽并且该列中有一个条目 |
 |很短,后面会加点以帮助排列。 |
 |使用此选项仅打印空格,不打印点。 |
 | |
 | -dotcols :使用它来指定具有点的特定列 |
 | (请参阅 -nodots 选项)。必须是逗号 |
 |不带空格的分隔正整数列表。 |
 | |
 | -cols :使用它指定要输出的列的子集。 |
 |是逗号分隔的正整数列表 |
 |和/或正整数的范围。有效的例子 |
 |列表为:4、6、12 或 4-10 或 1-4、12、15、4-7。专栏 |
 |可以重复并且不必按数字顺序。 |
 | |
 |注意:这个脚本是从一个更复杂的脚本中破解的,所以|
 |代码充满了各种不相关的东西。 |
  -------------------------------------------------- ------------------------

相关内容