我有一个像下面这样的文件
AT AT AG AG
GC GC GG GC
我想提取每个列的第一个和最后一个字符 n 将它们存储在两个不同的文件中
文件1:
A A A A
G G G G
文件2:
T T G G
C C G C
我的输入文件非常大。这是我可以在 awk 或 sed 中做到的方式吗
使用 GNU awk 进行 gensub():
gawk '{
print gensub(/.( |$)/,"","g") > "file1"
print gensub(/(^| )./,"","g") > "file2"
}' file
您可以使用 gsub() 和几个变量在任何 awk 中执行类似操作。
你可以试试这个:
写在 test.awk
#!/usr/bin/awk -f
BEGIN {
# FS = "[\s]+"
outfile_head="file1"
outfile_tail="file2"
}
{
num = NF
for(i = 1; i <= NF; i++) {
printf "%s ", substr($i, 0, 1) >> outfile_head
printf "%s ", substr($i, length($i), 1) >> outfile_tail
}
}
然后你运行这个: ./test.awk 文件
编辑 1:针对您的多行编辑进行了修改。
如果您打算编辑和共享它,您可以编写一个 perl 脚本并传入文件名。这只会遍历文件一次,并且不需要将文件存储在内存中。
文件“seq.pl”:
#!/usr/bin/perl
open(F1,">>$ARGV[1]");
open(F2,">>$ARGV[2]");
open(DATA,"$ARGV[0]");
while($line=<DATA>) {
$line =~ s/(\r|\n)+//g;
@pairs = split(/\s/, $line);
for $pair(@pairs) {
@bases = split(//,$pair);
print F1 $bases[0]." ";
print F2 $bases[length($bases)-1]." ";
}
print F1 "\n";
print F2 "\n";
}
close(F1);
close(F2);
close(DATA);
像这样执行它:
perl seq.pl full.seq f1.seq f2.seq
文件“full.seq”:
AT AT AG AG
GC GC GG GC
AT AT GC GC
文件“f1.seq”:
A A A A
G G G G
A A G G
文件“f2.seq”:
T T G G
C C G C
T T C C
两遍很容易做到:
sed 's/\([^ ]\)[^ ]/\1/g' file > file1
sed 's/[^ ]\([^ ]\)/\1/g' file > file2
一次完成是一项挑战......