1. 程式人生 > 實用技巧 >Linux中 2>&1 的含義

Linux中 2>&1 的含義

平時寫shell指令碼時經常見到命令或者定時任務的後面跟著2>&1的寫法,舉個例子大概如下面這樣

定時任務中
0 */1 * * *  root /bin/sh /opt/log_clear.sh >/dev/null 2>&1
普通shell指令碼中
yum install -y MariaDB-Galera-server MariaDB-client rsync >install.log 2>&1
echo 'net.ipv4.ip_forward = 1' >>/etc/sysctl.conf >/dev/null 2>&1

這個 /dev/null 不用多說了,相當於一個黑洞,Linux的所有資料進去後都會被直接丟棄,從裡面讀也不會讀出任何資料,如果希望執行某個命令,但又不希望在螢幕上顯示輸出結果,那麼可以將輸出重定向到 /dev/null

解釋後面的2>&1的之前,先說Linux的三個輸入輸出標準,0 通常指標準輸入(STDIN),1 是標準輸出(STDOUT),2 是標準錯誤輸出(STDERR),上面2>&1中的2和1就是分別對應著標準錯誤輸出(STDERR)和標準輸出(STDOUT),而 >& 是一個符號,不能拆開,意思是合併兩個輸出檔案,所以2>&1的含義就是將標準錯誤輸出合併到標準輸出

舉個例子驗證一下

[root@proxynode tomcat]# ls       //目錄下原來有兩個檔案
readme.txt  tomcat.tar.gz
[root@proxynode tomcat]#
[root@proxynode tomcat]# ls >a    //查詢檔案將結果重定向到a裡面,下面命令可以看到a裡面有正確的內容
[root@proxynode tomcat]# cat a
a
readme.txt
tomcat.tar.gz
[root@proxynode tomcat]# rm -f a
[root@proxynode tomcat]#
[root@proxynode tomcat]# 
ls 1>a //這裡可以看到加了1和上面不加1效果一樣,因為這裡1就是標準輸出的意思 [root@proxynode tomcat]# cat a a readme.txt tomcat.tar.gz [root@proxynode tomcat]# rm -f a [root@proxynode tomcat]# [root@proxynode tomcat]# ls 2>a //將錯誤重定向到a裡面,可以看到a是空的,因為沒有錯誤資訊,標準資訊沒指定直接輸出到控制檯了 a readme.txt tomcat.tar.gz [root@proxynode tomcat]# [root@proxynode tomcat]# cat a [root@proxynode tomcat]#

再來看關於錯誤輸出的和最終組合的結果

[root@proxynode tomcat]# ls
readme.txt  tomcat.tar.gz
[root@proxynode tomcat]# ls test   //test檔案不存在所以報錯了,沒指定輸出直接控制檯輸出
ls: cannot access test: No such file or directory
[root@proxynode tomcat]#

[root@proxynode tomcat]#
[root@proxynode tomcat]# ls test >a //這個是隻將正確資訊重定向,錯誤資訊還是控制檯直接輸出了
ls: cannot access test: No such file or directory
[root@proxynode tomcat]# cat a //上面命令會報錯,所以檔案裡是空的
[root@proxynode tomcat]# rm -f a
[root@proxynode tomcat]#

[root@proxynode tomcat]# ls test 2>a   //指定錯誤資訊重定向到a,下面看到a的內容包含了錯誤資訊
[root@proxynode tomcat]# cat a
ls: cannot access test: No such file or directory
[root@proxynode tomcat]#
[root@proxynode tomcat]# rm -f a
[root@proxynode tomcat]#
[root@proxynode tomcat]# ls test >a 2>&1   //看最終2>&1組合,輸出錯誤資訊
[root@proxynode tomcat]# cat a
ls: cannot access test: No such file or directory
[root@proxynode tomcat]#
[root@proxynode tomcat]# rm -f a
[root@proxynode tomcat]#
[root@proxynode tomcat]# ls >a 2>&1   //看最終2>&1組合,輸出正確資訊
[root@proxynode tomcat]# cat a  //通過這兩個組合可以看出來,加上2>&1後,不管是正確資訊還是錯誤資訊,都被重定向到了a中,跟我們上面解釋的概念一樣
a
readme.txt
tomcat.tar.gz
[root@proxynode tomcat]#

最後簡單再說明一下整個過程,例如這個命令

以下面這個命令為例 
yum install -y MariaDB-Galera-server >/dev/null 2>&1

執行前一部分yum install -y MariaDB-Galera-server的時候,會把結果輸出到控制檯
後面到了>/dev/null之後,即1>/dev/null,把標準輸出的結果重定向到了/dev/null中丟棄了
在執行到後一段2>&1時,2和1也合併了,上面1已經丟棄了這樣2的異常資訊也就跟丟棄了,控制檯上不會顯示任何結果

最後貼個Linux輸入輸出重定向的命令

command > file 將輸出重定向到 file。
command < file 將輸入重定向到 file。
command >> file 將輸出以追加的方式重定向到 file。
n > file 將檔案描述符為 n 的檔案重定向到 file。
n >> file 將檔案描述符為 n 的檔案以追加的方式重定向到 file。
n >& m 將輸出檔案 m 和 n 合併。
n <& m 將輸入檔案 m 和 n 合併。
<< tag 將開始標記 tag 和結束標記 tag 之間的內容作為輸入。