Echo mehrere Variablen in der gleichen Zeile Bash
Will ich echo zwei Variablen in der gleichen Zeile.
Ich will speichern 2015-03-04.01.Abhi_Ram.txt in einer Variablen mit dem Namen und 10 in eine variable ZÄHLEN und echo gleichzeitig.
Sample.txt
2015-03-04.01.Abhi_Ram.txt 10
2015-03-04.02.Abhi_Ram.txt 70
Unten ist der code, den ich kam mit:
for line in `hadoop fs -cat sample.txt`
do
VAR="${line}"
FILENAME=`echo ${VAR}|awk '{print $1}'`
COUNT=`echo ${VAR}|awk '{print $2}'`
COUNT_DT=`date "+%Y-%m-%d %H:%M:%S"`
echo db"|"Abhi_Ram"|"record_count"|"${FILENAME}"||"${COUNT}"||"${COUNT_DT} >> output.txt
done
I want the output as:
db|Abhi_Ram|record_count|2015-03-04.01.Abhi_Ram.txt||10||timestamp
db|Abhi_Ram|record_count|2015-03-04.02.Abhi_Ram.txt||70||timestamp
I'm getting the output as:
db|Abhi_Ram|record_count|2015-03-04.01.Abhi_Ram.txt||||Zeitstempel
db|Abhi_Ram|record_count|10||||Zeitstempel
db|Abhi_Ram|record_count|2015-03-04.02.Abhi_Ram.txt||||Zeitstempel
db|Abhi_Ram|record_count|70||||timestamp
Könnte mir jemand zeigen, was ich bin fehlt?
date
außerhalb, die nur einmal ausgeführt, bevor die Schleife beginnt.Auch, wenn Sie eine neue genug bash (4.1 oder 4.2), gibt es ein
printf
builtin für die Formatierung des Datums, Verwendung der externen date
Befehl überflüssig.InformationsquelleAutor AS0207 | 2015-08-10
Du musst angemeldet sein, um einen Kommentar abzugeben.
Betrachten:
Dies erzeugt die Datei:
Hinweise:
Ist es am besten Praxis, um klein-oder gemischter groß - /Kleinschreibung für Ihre shell-Variablen. Das system verwendet Großbuchstaben Variablen, und Sie wollen nicht versehentlich überschrieben werden.
Den vielen double-quotes in der
echo
- Anweisung überflüssig waren. Die gesamte Ausgabe-Zeichenkette kann in einem double-quoted string.Wenn Sie möchten, um eine Datei Lesen eine Zeile zu einem Zeitpunkt, ist es sicherer, verwenden die
while read ... done <inputfile
konstruieren. Dieread
- Anweisung erlaubt es uns auch zu leicht definierenfilename
undcount
Variablen.Für Befehls-substitution, viele bevorzugen die form
$(...)
über den backtick form. Dies ist, weil (a) die$(...)
macht den Anfang und Ende des Kommando-substitution deutlich sichtbar, (b) die$(...)
form Nester gut, und (c) nicht alle Schriften zeigen deutlich backticks als unterscheidet sich vom normalen Zecken. (Dank Chepner.)Für die Effizienz, die Umleitung zu
output.txt
wurde verschoben, um das Ende der Schleife. Auf diese Weise, die Datei wird nur geöffnet und einmal geschlossen. (Dank Charles Duffy.)Es sei denn, Sie müssen
count_dt
aktualisiert mit jedem einzelnen Eintrag, aber es könnte platziert werden, bevor die Schleife und legen Sie einfach mal jedes mal wennsample.txt
verarbeitet wurde. Wenn Sie ein up-to-date-version von bash (kein Mac OSX), dann diecount_dt
Zuweisung ersetzt werden kann (Dank Charles Duffy) mit einer nativen bash-Anweisung (keine Beschuss aus erforderlich):read -r
zu vermeiden, fallen backslash-Literale. (Zugegeben, Sie sind nicht wahrscheinlich in Dateinamen, aber Sie sind möglich).Ich würde auch empfehlen, eine
>output.txt
auf der außerhalb der Schleife, so dass Sie nur öffnen Sieoutput.txt
einmal, eher als re-öffnen Sie die Datei jedes mal, wenn Sieecho
, als getan, mit der>>output.txt
auf der echo-Befehl.Gute Idee. Antwort aktualisiert und verschieben Sie die Umleitung außerhalb der Schleife.
(Wäre auch erheblich verbessern, die Effizienz zu berechnen
count_dt
außerhalb der Schleife... oder nutzen Sie die glänzenden neuen letzten-4.x-featureprintf -v count_dt '%(%Y-%m-%d %H:%M:%S)T' -1
zu tun, die Berechnung in native bash anstatt Beschuss aus auf eine externedate
Befehl für jede Zeile verarbeitet wird).Schön! Dass
printf
ist mir neu.InformationsquelleAutor John1024
John1024 hat erklärt, wie dies zu tun ist richtig; ich würde mir gern einen Blick auf, warum die ursprüngliche version hat nicht funktioniert. Das grundlegende problem ist, dass
for
Schleifen über Worte, nicht über Linien. Die Datei hat zwei Wörter auf jeder Zeile (Dateiname und Anzahl), so läuft die Schleife zweimal pro Linie. Um dies zu sehen, versuchen Sie:...und es gibt so etwas wie:
...das ist nicht, was Sie wollen, überhaupt. Es hat auch noch einige andere unangenehme Macken, wie wenn die input-Datei enthielt das Wort "*", es hätte einfügen eine Liste der Dateinamen im aktuellen Verzeichnis.
Den
while read ... done <file
Ansatz ist der richtige Weg zu Durchlaufen Linien in einem shell-Skript. Es passiert einfach, auch in der Lage sein, um split jede Zeile in Felder die zimmerreserviereung, ohne das Durcheinander mitawk
(in diesem Fallread filename count
funktioniert).InformationsquelleAutor Gordon Davisson