所以……我知道我可以使用tac或其他一些工具来反转文件中的行顺序,但是如何在其他维度(即水平?)重新排序?我正在尝试使用以下awk脚本:
{ out=""; for(i=length($0);i>0;i--) { out=out substr($0,i,1)} print out; }
这似乎扭转了角色,但它是乱码,我不明白为什么.我错过了什么?
我在awk中这样做,但还有更好的东西吗?也许是?
这是一个例子.输入数据如下所示:
$cowsay <<<"hello" _______ < hello > ------- \ ^__^ \ (oo)\_______ (__)\ )\/\ ||----w | || ||
输出看起来像这样:
$cowsay <<<"hello" | rev _______ > olleh < ------- ^__^ \ _______\)oo( \ \/\) \)__( | w----|| || ||
请注意,无论是使用rev还是我自己的awk脚本,输出都是相同的.正如你所看到的,事情是相反的,但……它被破坏了.
解决方法
转速很好,但它不填充输入线.它只是逆转了它们.
你看到的“破坏”是因为一行可能是20个字符长,而下一行可能是15个字符长.在输入文本中,它们共享一个左侧列.但是在输出文本中,他们需要共享一个右侧列.
所以你需要填充.哦,和不对称的逆转,正如约阿希姆所说.
这是我的意见:
#!/usr/bin/awk -f # length($0)>max { max=length($0); } { # Reverse the line... for(i=length($0);i>0;i--) { o[NR]=o[NR] substr($0,1); } } END { for(i=1;i<=NR;i++) { # prepend the output with sufficient padding fmt=sprintf("%%%ds%%s\n",max-length(o[i])); printf(fmt,"",o[i]); } }
(我是用gawk做的;我认为我没有使用任何gawkisms,但如果你使用更经典的awk变种,你可能需要调整它.)
使用方法与使用rev的方式相同.
ghoti@pc:~$echo hello | cowsay | ./revawk | tr '[[]()<>/\\]' '[][)(><\\/]' _______ < olleh > ------- ^__^ / _______/(oo) / /\/( /(__) | w----|| || ||
如果您愿意这样做,您甚至可以通过将其添加到最后一个printf行来从awk脚本中运行translate:
printf(fmt," ",o[i]) | "tr '[[]()<>/\\]' '[][)(><\\/]'";
但我不推荐它,因为它使revawk命令对其他应用程序不那么有用.