匹配文件的第一列与awk,引号有困难

Son*_*ein 3 bash awk

我的输入文件如下所示

Chr1 1
Chr1 2
Chr2 3
Run Code Online (Sandbox Code Playgroud)

我想根据第一列中的Chr将输入文件拆分为多个文件.

应该有两个输出文件输出文件1(名为tmpChr1):

Chr1 1
Chr1 2
Run Code Online (Sandbox Code Playgroud)

输出文件2(名为tmpChr2):

Chr2 3
Run Code Online (Sandbox Code Playgroud)

这是迄今为止的代码:

#!/bin/bash

for((chrom=1;chrom<30;chrom++)); do
echo Chr${chrom}
chr=Chr${chrom}
awk "\$1==$chr{print \$1}" input.txt > tmp$chr
done
Run Code Online (Sandbox Code Playgroud)

这条线awk "\$1==$chr{print \$1}"是问题,awk似乎需要在$ chr附近引用以正确匹配$ 1

awk '$1=="Chr1"{print $1}' 工作和tmpChr1

awk '$1=="$chr"{print $1}' 也不起作用

也没有 awk "$1=='$chr'{print $1}"

真的在报价上挣扎,有人能说清楚我应该做些什么吗?

Ed *_*ton 7

永远不要在awk脚本周围使用双引号,并且绝不允许shell变量作为awk脚本主体的一部分进行扩展.请参阅http://cfajohnson.com/shell/cus-faq-2.html#Q24

尽管如此,你仍然可以通过一般方法取消标记.你只需要这个awk脚本:

awk '{print > ("tmp"$1)}' file
Run Code Online (Sandbox Code Playgroud)

看:

$ ls
file
$ cat file
Chr1 1
Chr1 2
Chr2 3
$ awk '{print > ("tmp"$1)}' file
$ ls
file  tmpChr1  tmpChr2
$ cat tmpChr1
Chr1 1
Chr1 2
$ cat tmpChr2
Chr2 3
Run Code Online (Sandbox Code Playgroud)

无论何时在shell中编写循环只是为了操作文本,你都有错误的方法.UNIX shell是一种环境,可以使用该语言调用工具来对这些调用进行排序.用于操作文本的UNIX工具是awk.因此,如果您需要在UNIX中操作文本,请编写一个awk脚本并从shell调用它,这就是全部.

  • 它与shell中的相同 - 重定向输出.尽管如此,与shell相比,awk中```和`>>`的语义有一些小而重要的区别.获得由Arnold Robbins撰写的Effective Awk Programming,第4版. (2认同)