Ich habe ein C-Programm, das Befehlszeilenargumente von argv liest. Ist es möglich, eine Pipe zu erstellen, um den Inhalt einer Datei als Befehlszeilenargumente zu meinem Programm umzuleiten? Angenommen, ich habe eine Datei arguments.dat
mit diesem Inhalt:
0 0.2 302 0
Und ich möchte, dass mein Programm aufgerufen wird mit:
./myprogram 0 0.2 302 0
Ich habe Folgendes versucht:
cat arguments.dat | ./myprogram
ohne Erfolg.
Antworten:
5 für die Antwort № 1Bei den meisten Shells können Sie den Inhalt einer Datei in eine Befehlszeile mit einfügen $(<filename)
:
./myprogram $(<arguments.dat)
Wenn Ihre Shell das nicht unterstützt, dann wird eine der älteren Methoden funktionieren:
./myprogram $(cat arguments.dat)
./myprogram `cat arguments.dat` # need this one with csh/tcsh
(Sie kennen den Unterschied zwischen Befehlszeilenargumenten und Dateieingabe, richtig? Warum sollten Sie erwarten, Befehlszeilenargumente in ein Programm einzubinden?)
11 für die Antwort № 2
xargs
ist deine Antwort:
cat arguments.dat | xargs ./myprogram
Oder einfacher:
xargs -a arguments.dat ./myprogram
Überprüfen Sie das Handbuch für die vielen Möglichkeiten zur Anpassung xargs
. Sie können z. B. Zeile für Zeile und nicht Wort für Wort lesen, und Sie können die Argumente für komplexere Ersetzungen verwenden.
2 für die Antwort № 3
... was zu sagen ist: Die folgenden Antworten gelten für Fälle, in denen dies nicht akzeptabel wäre ./myprogram --first-argument "first value"
leise verändert werden ./myprogram --first-argument; ./myprogram "first value"
.
Wenn Ihre Argumente ein Zeilen-Literal sind
Das heißt, wenn Ihre Eingabe wie folgt aussieht:
--first-argument
first value
--second-argument
second value
und du meinst das zu laufen:
./myprogram --first-argument "first value" --second-argument "second value"
... dann solltest du (mit bash 4.0 oder höher) verwenden:
readarray -t args <arguments.dat
./myprogram "${args[@]}"
... oder (auch für bash 3.x):
args=( )
while IFS= read -r arg; do
args+=( "$arg" )
done <arguments.dat
./myprogram "${args[@]}"
Wenn Ihre Argumente mit Anführungszeichen versehen sind, oder um zu unterscheiden, um sie zu unterscheiden
Das heißt, wenn Ihre Datei so etwas enthält (beachten Sie, dass sich Zeilenumbrüche und nicht angebene Leerzeichen hier identisch verhalten):
--first-argument "first value"
--second-argument "second value"
... und du meinst das zu laufen:
./myprogram --first-argument "first value" --second-argument "second value"
... dann solltest du verwenden:
args=( )
while IFS= read -r -d "" arg; do
args+=( "$arg" )
done < <(xargs printf "%s " <arguments.dat)
Wenn Sie Ihr Argumentformat steuern
Verwenden Sie NULL-getrennte Werte. Das heißt, erstellen Sie die Datei wie folgt:
printf "%s " "argument one" "argument two" >arguments.dat
... und analysiere es wie folgt:
args=( )
while IFS= read -r -d "" arg; do
args+=( "$arg" )
done <arguments.dat
./myprogram "${args[@]}"
Dies wird mit funktionieren alles möglich Argumentwerte, auch solche mit literalen Zeilenumbrüchen, wörtlichen Anführungszeichen, umgekehrten Schrägstrichen oder anderen nicht druckbaren Zeichen. (Wörtliche Nullen sind nicht möglich in UNIX-Befehlszeilen, da Befehlszeilen aus NUL-terminierten Strings bestehen; Daher ist NUL das einzige Zeichen, das völlig sicher ist, um Argumente in einem String eindeutig zu trennen.
Wenn Argumente über Aufrufe hinweg geteilt werden sollen
Dieser Unterabschnitt ist relevant, wenn das gewünschte Ergebnis vorliegt(Wenn es in Ihrer Datei mehr Argumente gibt, als an einen Aufruf Ihres Programms übergeben werden können), gibt es mehrere unterschiedliche Aufrufe des Programms, die jeweils eine Teilmenge von Argumenten erhalten. Dies ist eine Familie von Fällen, in denen xargs
ist das richtige Werkzeug für den Job.
Wenn Sie auf einer GNU-Plattform sind, möchten Sie vielleicht laufen xargs -a arguments.dat
anstatt stdin umzuleiten; Dies wird jedoch nicht mit BSD-Xargs (wie auf MacOS) unterstützt und wird daher hier nicht demonstriert.
Wenn Ihre Argumente ein Zeilen-Literal sind
Mit GNU xargs (die meisten Linux-Plattformen):
xargs -d $"n" ./myprogram <arguments.dat
Mit BSD xargs (MacOS, FreeBSD / OpenBSD / etc):
xargs -0 ./myprogram < <(tr "n" " " <arguments.dat)
Wenn Ihre Argumente mit Anführungszeichen versehen sind, oder um zu unterscheiden, um sie zu unterscheiden
xargs ./myprogram <arguments.dat
Wenn Sie NUL-getrennte Eingaben generiert haben
xargs -0 ./myprogram <arguments.dat