专栏名称: 生信媛
生信媛,从1人分享,到8人同行。坚持分享生信入门方法与课程,持续记录生信相关的分析pipeline, python和R在生物信息学中的利用。内容涵盖服务器使用、基因组转录组分析以及群体遗传。
目录
相关文章推荐
51好读  ›  专栏  ›  生信媛

学习生信必须掌握的技能-第二部分

生信媛  · 公众号  · 生物  · 2019-08-28 18:43

正文

请到「今天看啥」查看全文


阅读原文体验更棒


C harpter 3

这一章我觉得大家是可以好好看看的,这里面作者提到了一些我们有时候不太注意的概念:

  • streams

  • redirection

  • pipes

  • working with running programs

  • command substitution

Working with Streams and Redirection

  • Working with Streams and Redirection Unix利用stream(流)这种文本处理哲学对于生信是非常有用的,它允许我们处理数据之间的流,而非将数据一股脑地保存在内存里面。想象一下,如果你想要整合两个超大的文件在一起,正常操作是,打开一个大文件,复制,然后打开另一个大文件,粘贴到另一个大文件里面。这里的每一步都会耗费很大的内存。但Unix则会将整合的两个大文件的内容打印到 standard output stream(标准输出流) ,然后我们可以从终端重定向标准输出流到我们想要的文件。

  • Redirecting Standard Error 标准错误流是用来输出errors, warnings, and messages meant to be read by the user。

    默认情况下,标准输出流和标准错误流如果没有重定向的话,都是输出到终端上的。但也可以输出到文件。

     $ ls -l tb1.fasta leafy1.fasta
     ls: leafy1.fasta: No such file or directory
     -rw-r--r-- 1 vinceb staff 0 Feb 21 21:58 tb1.fasta
     
     $ ls -l tb1.fasta leafy1.fasta > listing.txt 2> listing.stderr
     $ cat listing.txt
     -rw-r--r-- 1 vinceb staff 152 Jan 20 21:24 tb1.fasta
     $ cat listing.stderr
     ls: leafy1.fasta: No such file or directory
     
     $ ls -l tb1.fasta leafy1.fasta > listing.txt 2>&1
  • 有时候,我们并不想输出报错信息,或者输出物理储存里可能会拖慢程序的速度,这时候Unix操作系统就为我们提供了一个虚假的储存(pseudodevice):/dev/null 。凡是写到/dev/null里的都会消失。

  • tail有一个骚操作是tail -f。设想一下你把标准错误流写到了stderr.txt文件里面,你可能会用tail时不时地看下,看有什么报错信息。但用了tail -f,你就可以持续地监控这个文件了。

  • Using Standard Input Redirection Unix也提供一种叫标准输入流(standard input )的重定向操作。通常情况下,标准输入流是来自于你的键盘。但是用 < 这个重定向操作符,我们也可以直接从一个文件里面读取标准输入流。

     # 从inputfile输入标准输入流,然后标准输出流到outputfile
     $ program < inputfile > outputfile

    事实上,许多程序也可以直接用file参数来读取文件,而不通过标准输入流。有些程序(生信里面很多)则会用 - 这个符号来表示他们应该用标准输入流。

  • The Almighty Unix Pipe: Speed and Beauty in One 管道跟我们上面提到的重定向很像,但其不是重定向一个程序的结果到一个文件,而是把程序的结果重定向成另一个程序的标准输入。但标准错误还是定向到你的终端屏幕上。

  • 管道可以连接grep,cat等一系列程序。还可以连接其他语言的输入和输出。

  • Combining Pipes and Redirection 假如progarm 1是对input.txt 执行操作,然后输出结果到标准输出流,输出诊断结果到标准错误流。而program 2则是接受program 1的输出作为输入,然后也输出诊断结果到标准错误流。这时候,如果我们还是按正常操作,program 1和2的诊断结果就会在屏幕上混淆。但我们可以这样

     program1 input.txt 2> program1.stderr | \
     program2 2> program2.stderr > results.txt
  • 因为管道只能连接 标准输出流 。但如果我们想同时在结果里面看到标准输出流和标准错误流的信息。那么就可以把标准错误流重定向到标准输出流那里。

     # 2>&1 操作就是把标准错误流重定向到标准输出流
     $ program1 2>&1 | grep "error"
  • Even More Redirection: A tee in Your Pipe 另一个骚操作:储存中间文件。

     # 用了tee操作,既可以把program1的标准输出流储存成中间文件,也可以输出给program2
     $ program1 input.txt | tee intermediate-file.txt | program2 > results.txt

Managing and Interacting with Processes

这里提到了

  • running and managing processes in the background

  • killing errant processes

  • checking process exit status

  • 当我们在shell里面开始运行命令之后,我们是不能再对shell进行操作的。短的命令还好,长的命令就非常地蛋疼了。这时候我们就可以在运行命令时候加入 &,来让其在后台运行。

     # 这里的26577是proces ID或者说PID(进程ID)
     $ program1 input.txt > results.txt &
     [1] 26577
     
     # 这里的1是jobs IDs
     $ jobs
     [1]+ Running program1 input.txt > results.txt
  • 为了把后台运行的命令带到前台来,就可以用fg(for foreground)命令。当你的后台有许多的命令的时候,fg % 就可以选择把对应的进程带到前台来。

    就是所谓的jobs ID。

    当你的后台进程只有一个的时候,fg和fg %1是等效的。

  • 关闭我们的终端,会发送一个Hangup signal(SIGHUP)信号给由已关闭终端之前开启的所有进程。然后那些进程受到这些信号之后,几乎都会立刻停止运行。

  • 也可以把前台运行的放到后台去。这时候你需要先用ctrl+z发送挂起信号(suspend),程序就会暂停。然后再用bg % 放到后台。

     $ program1 input.txt > results.txt # forgot to append ampersand
     $ # enter control-z
     [1]+ Stopped program1 input.txt > results.txt
     $ bg
     [1]+ program1 input.txt > results.txt
  • 杀进程这部分详细内容在作者Github这一章节的README上有。

  • Exit Status: How to Programmatically Tell Whether Your Command Worked :Exit Status退出码可以帮助我们知晓一个程序是否正确地运行完成了。标准地来说,0 exit status就代表程序正确运行了,非0就代表不正确。

    这就是有时候你程序跑错了,经常会出现的Exit status XXX

    $?代表了退出码

     $ program1 input.txt > results.txt
     $ echo $?
     0

    有时候,开发者在开放一款软件的时候,会忘记考虑到退出码这种情况。所以你会发现有时候错误地运行了,还是zero-exit status。

  • 退出码是很有用的,因为他可以让我们链式地编程。即后一个命令是否执行取决于前一个命令的退出码。

     # 前一个命令成功,就执行后续命令(&&)
     # 防止程序1失败了,程序2还是读这个文件
     
     $ program1 input.txt > intermediate-results.txt && \
     program2 intermediate-results.txt > results.txt
     
     
     
     # 前一个命令失败,就执行后续命令(||)
     # 在输出warning的时候比较有用
     $ program1 input.txt > intermediate-results.txt || \
     echo "warning: an error occurred"

    如果状态码,只想连续执行的话。就用 ;

Command Substitution

  • 命令替换可以把一个命令的输出结果,嵌入另一个命令里面

     $ grep -c '^>' input.fasta
     416
     $ echo "There are $(grep -c '^>' input.fasta) entries in my FASTA file."
     There are 416 entries in my FASTA file.

    $()和``是等价的

  • 使用这个命令,我们可以很方便地创建当前时间文件夹

     $ mkdir results-$(date +%F)
     $ ls results-2015-04-13

    +%F 这种格式对于日期命令的文件夹是很有帮助的,因为到时候排序的时候就会按日期来排

     $ ls -l
     drwxr-xr-x 2 vinceb staff 68 Feb 3 23:23 1999-07-01
     drwxr-xr-x 2 vinceb staff 68 Feb 3 23:22 2000-12-19
     drwxr-xr-x 2 vinceb staff 68 Feb 3 23:22 2011-02-03
     drwxr-xr-x 2 vinceb staff 68 Feb 3 23:22 2012-02-13
     drwxr-xr-x 2 vinceb staff 68 Feb 3 23:23 2012-05-26
     drwxr-xr-x 2 vinceb staff 68 Feb 3 23:22 2012-05-27
     drwxr-xr-x 2 vinceb staff 68 Feb 3 23:23 2012-07-04
     drwxr-xr-x 2 vinceb staff 68 Feb 3 23:23 2012-07-0








请到「今天看啥」查看全文