Shell-Standardstreams Umleitungsreihenfolge ODER 2> & 1 1 / dev / null vs 1> / dev / null 2> & 1

2778
Wakan Tanka

Kann jemand bitte die Unterschiede erklären? Werden einige davon als Best Practice betrachtet? Wenn ich mich richtig erinnere, habe ich irgendwie auf SO gelesen, dass dies dem 1>/dev/nullvorausgehen sollte:2>&1

ls -al /doesNotExists 2>&1 1>/dev/null ls -al /doesNotExists 1>/dev/null 2>&1  ls -al /doesNotExists 1>&2 2>/dev/null ls -al /doesNotExists 2>/dev/null 1>&2  ls -la /doesNotExists 2<&1 1>/dev/null ls -la /doesNotExists 2<&1 2>/dev/null  ls -la /doesNotExists 1<&2 1>/dev/null ls -la /doesNotExists 1<&2 2>/dev/null  ls -la /doesNotExists 1>/dev/null 2<&1 ls -la /doesNotExists 2>/dev/null 2<&1  ls -la /doesNotExists 1>/dev/null 1<&2 ls -la /doesNotExists 2>/dev/null 1<&2 
3
Lesen Sie "n> & m" als, ** umleiten Sie den Stream "n" dorthin, wo "m" momentan zu ** geleitet wird. Stream "n" nicht zum Stream "m" umleiten. ctrl-alt-delor vor 9 Jahren 2
Mögliches Duplikat von [Was bewirkt "2> & 1" in der Befehlszeile?] (http://superuser.com/questions/71428/what-does-21-do-in-command-line) Scott vor 9 Jahren 0

1 Antwort auf die Frage

6
DavidPostill

Shell-Standard-Streams-Umleitungsreihenfolge

Die Reihenfolge ist wichtig, da das Ergebnis anders ist. Nimm dein erstes Beispiel:

ls -al /doesNotExists 2>&1 1>/dev/null 

Dadurch wird nur die Standardausgabe an NUL weitergeleitet, da der Standardfehler an die Standardausgabe dupliziert wurde, bevor die Standardausgabe an die Verzeichnisliste umgeleitet wurde.

ls -al /doesNotExists 1>/dev/null 2>&1 

Dies leitet sowohl die Standardausgabe als auch den Standardfehler auf nul.


Bash-Referenzhandbuch: Umleitungen

Beachten Sie, dass die Reihenfolge der Weiterleitungen von Bedeutung ist. Zum Beispiel der Befehl

ls > dirlist 2>&1 

leitet die Standardausgabe (Dateideskriptor 1) und den Standardfehler (Dateideskriptor 2) während des Befehls an die Dateiliste

ls 2>&1 > dirlist 

Leitet nur die Standardausgabe an die Dateiliste, da der Standardfehler vor der Umleitung der Standardausgabe auf die Verzeichnisliste kopiert wurde.

Source Bash-Referenzhandbuch: Umleitungen


Tutorial

Im Illustrated Redirection Tutorial gibt es ein schönes illustriertes Tutorial, das dies verständlicher macht:

Umleitungsreihenfolge, dh "> Datei 2> & 1" vs. "2> & 1> Datei"

Es spielt keine Rolle, wo die Umleitungen in der Befehlszeile angezeigt werden, ihre Reihenfolge ist jedoch wichtig. Sie sind von links nach rechts eingerichtet.

2>&1 >file 

Ein häufiger Fehler ist, den Befehl 2> & 1> file auszuführen, um stderr und stdout in die Datei umzuleiten. Mal sehen was los ist. Zuerst geben wir den Befehl in unser typisches Terminal ein, die Deskriptoren sehen folgendermaßen aus:

 --- +-----------------------+ standard input ( 0 ) ---->| /dev/pts/5 | --- +-----------------------+  --- +-----------------------+ standard output ( 1 ) ---->| /dev/pts/5 | --- +-----------------------+  --- +-----------------------+ standard error ( 2 ) ---->| /dev/pts/5 | --- +-----------------------+ 

Dann sieht unsere Shell, Bash 2> & 1, so dass sie 1 dupliziert, und der Dateideskriptor sieht folgendermaßen aus:

 --- +-----------------------+ standard input ( 0 ) ---->| /dev/pts/5 | --- +-----------------------+  --- +-----------------------+ standard output ( 1 ) ---->| /dev/pts/5 | --- +-----------------------+  --- +-----------------------+ standard error ( 2 ) ---->| /dev/pts/5 | --- +-----------------------+ 

Richtig, nichts hat sich geändert, 2 wies bereits auf dieselbe Stelle wie 1. Nun sieht Bash> file und ändert somit stdout:

 --- +-----------------------+ standard input ( 0 ) ---->| /dev/pts/5 | --- +-----------------------+  --- +-----------------------+ standard output ( 1 ) ---->| file | --- +-----------------------+  --- +-----------------------+ standard error ( 2 ) ---->| /dev/pts/5 | --- +-----------------------+ 

Und das wollen wir nicht.

>file 2>&1 

Schauen wir uns nun den richtigen Befehl an> Datei 2> & 1. Wir beginnen wie im vorherigen Beispiel und Bash sieht> file:

 --- +-----------------------+ standard input ( 0 ) ---->| /dev/pts/5 | --- +-----------------------+  --- +-----------------------+ standard output ( 1 ) ---->| file | --- +-----------------------+  --- +-----------------------+ standard error ( 2 ) ---->| /dev/pts/5 | --- +-----------------------+ 

Dann sieht es unsere Duplikation 2> & 1:

 --- +-----------------------+ standard input ( 0 ) ---->| /dev/pts/5 | --- +-----------------------+  --- +-----------------------+ standard output ( 1 ) ---->| file | --- +-----------------------+  --- +-----------------------+ standard error ( 2 ) ---->| file | --- +-----------------------+ 

Und voila, sowohl 1 als auch 2 werden in die Datei umgeleitet.

Danke, schöne Infografik. Nur zwei Klarstellungen: 1. `ls> / dev / null` ist dasselbe wie` ls 1> / dev / null` 2. Wann werden `<` verwendet? Ich habe `ls -l> file & 1 <2` ausprobiert und es ist nicht dasselbe wie` ls> file 2> & 1`. Ist `cat file` gleichbedeutend mit` cat Wakan Tanka vor 9 Jahren 0
@ WakanTanka 1 / yes (1 bedeutet nur Standardausgabe). 2 / <wird verwendet, um _input_ umzuleiten (cat-Datei ist identisch mit cat <-Datei) DavidPostill vor 9 Jahren 0
Wenn es sinnvoll ist, die Eingabe umzuleiten, kann sie wie gezeigt geöffnet werden. Warum umleiten? Wakan Tanka vor 9 Jahren 0
Nur um die Antwort im Kommentar zu verdeutlichen: `cat Tiago vor 8 Jahren 0
Diese Erklärung ist sehr nett. Danke für das Diagramm. Jingguo Yao vor 7 Jahren 0