问题 如何处理bash中的每一行


我想打印奇数行(1,3,5,7 ..)而没有任何改变,但偶数行(2,4,6,8)处理以grep开头的管道。我想把所有内容写入新文件(奇数行没有任何变化,偶数行的新值)。

我知道如何在awk中打​​印每一行:

awk ' NR % 2 == 1 { print; } NR % 2 ==0 {print; }' file.fasta

但是,对于偶数行,我不想使用 {print; } 但我想用我的grep管道代替。

建议将不胜感激。非常感谢。


12373
2017-07-19 12:07


起源

该 ==1{print;} 简直就是多余的 awk 'NR%2' will print odd lines - Kevin
谢谢大家的帮助! - Perlnika


答案:


如果你打算做一个简单的事情 grep,你可以取消额外的步骤并在awk中进行过滤,例如:

awk 'NR % 2 {print} !(NR % 2) && /pattern/ {print}' file.fasta

但是,如果你打算做更多的话,那就像 chepner已经指出了,你确实可以从awk内部管道。例如:

awk 'NR % 2 {print} !(NR % 2) {print | "grep pattern | rev" }' file.fasta

这打开了命令的管道 "pattern | rev" (注意周围的引号)并将打印输出重定向到它。请注意,这种情况下的输出可能不像您预期​​的那样;你将最终输出所有奇数行,然后输出管道命令(消耗偶数行)。


(根据您的评论)计算每个偶数行中的字符数,请尝试:

awk 'NR % 2 {print} !(NR % 2) {print length($0)}' file.fasta

9
2017-07-19 12:19



谢谢。我将计算偶数行中的字母数。 - Perlnika
@Perlnika你可以得到使用的字符数 length 在awk中命令。查看更新的答案。 - Shawn Chin
@Perlnika,一些fasta文件可能包含奇怪的字符 - 要么 X,但你可能已经回答了OP想要的东西。 - Steve
@steve谢谢,但这个awk脚本只打印偶数行 - Perlnika
@ShawnChin非常感谢,我使用0美元代替0而且它有效! - Perlnika


你可以直接从里面管道 awk

awk ' NR % 2 == 1 { print; } NR % 2 ==0 {print | "grep -o [actgnACTGN] | wc -l"; }' file.fasta

但请注意,这不会保留输入文件的顺序。

(选择的答案对于手头的任务更好,但我将这里留下这个答案作为将print语句传递给外部命令的示例。)


6
2017-07-19 12:13



谢谢,我用awk'NR%2 == 1 {print; } NR%2 == 0 {print | grep -o [actgnACTGN] | wc -l}'file.fasta(为了计算行中的字母数)但是wc声明有问题:awk:第1行:wc处或附近的语法错误(所以我猜问题在我的管道中:) - Perlnika
不保留秩序是什么意思? - Perlnika
@Perlnika他的意思是你最终将输出所有奇数行,然后输出管道(消耗所有偶数行) - Shawn Chin
在我跑的短测试中,打印了所有奇数行,然后是由输出的偶数行 grep。这是因为grep的输出可能需要与输出合并 awk,这可能是非确定性的。此外,这可能是低效的,因为我认为是单独的 grep 为每个偶数行分叉。 - chepner
抱歉,引号中有错误,我认为我已修复。查看我的更新。 - chepner


为了使您的管道输出按AWK输出顺序显示,您需要在每次迭代时关闭管道。当然,这是非常低效的。

awk 'BEGIN{ cmd = "grep -io \047[actgn]\047 | wc -l" } NR % 2 { print } NR % 2 == 0 { print | cmd; close(cmd) }' file.fasta

您显然不想计算不在指定列表中的字符,所以 length($0) 不行。这将工作,应该比管道方法快得多:

awk 'NR % 2 { print } NR % 2 == 0 {n = split($0, a, /[^actgnACTGN]/); print length($0) - n + 1}' file.fasta

它的工作原理是使用你的字符分割线条  想要作为分隔符并从行的长度中减去子串的计数并添加1.本质上,它从行的长度中减去不需要的字符的数量,从而留下想要的字符的数量作为结果。


1
2017-07-19 13:58