两个变量在bash中的一个for循环中

时间:2014-12-10 22:07:20

标签: bash shell loops for-loop fastq

我有一个目录,里面有两种文件类型:* .sai和* fastq,我想在一个shell中使用这两个变量进行循环:

for j in *sai *fastq

 do bwa samse $j $j > ${j%.sai}.sam 

done;

在命令do之后我想将相应的* .sai和* .fastq数据加载到程序中(bwa samse)。你能用语法帮我吗?

实施例

一个目录中的

xx.fast xx.sai yy.fastq yy.sai,程序bwa samse需要一次处理两个相应的文件 - bwa samse xx.fastq xx.sai...

非常感谢任何想法。

4 个答案:

答案 0 :(得分:1)

尽量不要使用ls来提供循环。使用大括号扩展仅在您的循环中包含*.sai*.fastq个文件:

for j in ./*.{sai,fastq}
do
    ## do what you need to the *.sai & *.fastq files 
done

您还可以提供路径变量:

mypath=/path/to/files
for j in "${mypath}"/*.{sai,fastq}
(snip)

注意:不清楚bwa samse $j $j > ${j%\.*}.sam的作用。解释你需要如何处理文件,我可以进一步帮助..

如果存在一对一的关系(匹配.sai和.fastq文件),则只需:

for j in ./*.sai
do
    fname="${j%.*}"   # remove the extension ($fname is filename w/o ext)
    ## do what you need to the *.sai & *.fastq files 
    #  bwa samse "${fname}.sai" "${fname}.fastq" whatever else
done

答案 1 :(得分:1)

尝试使用bash parameter expansion执行此操作:

for j in .*sai; do  
    [[ -s ${j%.sai}.fastq ]] &&
        bwa samse "$j" "${j%.sai}.fastq" > "${j%.sai}.sam"     
done

并请,通过解析ls输出停止杀死小猫。 (不适合您的不可思议)

答案 2 :(得分:1)

使用GNU Parallel看起来像这样:

parallel bwa samse ref.fasta {} {.}.fastq '>' {.}.sam  ::: *.sai   

GNU Parallel是一个通用的并行程序,可以很容易地在同一台机器上或在你有ssh访问权限的多台机器上并行运行作业。它通常可以替换for循环。

如果要在4个CPU上运行32个不同的作业,并行化的直接方法是在每个CPU上运行8个作业:

Simple scheduling

GNU Parallel会在完成后生成一个新进程 - 保持CPU处于活动状态,从而节省时间:

GNU Parallel scheduling

<强>安装

如果没有为您的发行版打包GNU Parallel,您可以进行个人安装,不需要root访问权限。这可以在10秒内完成:

(wget -O - pi.dk/3 || curl pi.dk/3/ || fetch -o - http://pi.dk/3) | bash

有关其他安装选项,请参阅http://git.savannah.gnu.org/cgit/parallel.git/tree/README

了解详情

查看更多示例:http://www.gnu.org/software/parallel/man.html

观看介绍视频:https://www.youtube.com/playlist?list=PL284C9FF2488BC6D1

完成教程:http://www.gnu.org/software/parallel/parallel_tutorial.html

注册电子邮件列表以获得支持:https://lists.gnu.org/mailman/listinfo/parallel

答案 3 :(得分:0)

(编辑以反映评论 - 使用ls列出文件名是不必要的)

要删除文件扩展名,您需要使用${j%\.*},这将保留最后.之前的所有字符

for j in *.sai *.fastq
do
    bwa samse $j $j > ${j%\.*}.sam 
done;