用空格替换制表符以保持n个空格对齐

3

我试图自动比较两组包含列式数据的文件。这里有三个主要问题让这个任务变得棘手:

  1. A组和B组中的列排序不同
  2. A组使用制表符,而B组使用空格
  3. A组中有些列为空白,而在B组中会有一个默认值。

我尝试了一些简单的shell脚本来重新排列A组的列次序,例如 awk '{print substr($0, 10, 10) substr($0, 20, 10)}等等,但是在这组文件中使用制表符意味着列以不一致的字符号码开始。

我认为最简单的解决方法是用空格替换制表符,然后像上面那样使用awk重新排列数据。我应该如何用一定数量的空格替换制表符,使其到达下一个制表符停止点(假设为8)。

显然,用固定数量的空格替换制表符是行不通的,正如我下面测试的结果一样。

$ echo "A\tB\nA \tB\nA  \tB\nA   \tB\n" > test
$ cat test
A       B
A       B
A       B
A       B
$ cat test | sed 's/\t/    /g'
A    B
A     B
A      B
A       B

显然,可以通过编写一些代码来确定制表符所在的位置,并填充适当数量的空格字符以实现对齐,但似乎应该有比我可能忽略的更简单的解决方案。(或者打开vim中的每个文件并使用 :retab,但一定有更好的选择!)
注意:由于某些数据集中存在空白,我无法使用column重新排列数据。
2个回答

2

由于您在制表符之前有空格,因此可以使用以下sed命令:

sed $'s/ *\t/    /g' test
A    B
A    B
A    B
A    B 

这也会将制表符前的0个或多个空格替换为4个空格。

1
知道这一定是一些简单的东西 - 谢谢 - Silasvb

0
给出以下 awk 脚本:
BEGIN {
  tabSize = 8;
}
{
  str = $0;
  idx = index(str, "\t");
  while (idx > 0) {
    left = substr(str, 0, idx);
    right = substr(str, idx + 1);
    spaces = sprintf("% " ((tabSize + 1) - (idx % tabSize)) "s", "");
    str = left spaces right;
    idx = index(str, "\t");
  }
  print str;
}

您可以执行此命令:

cat test | awk -f tab2spaces.awk

这个脚本可以与任何内容一起使用。


它似乎什么也没做。 - Kouber Saparev

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接