Befehl zum „Ausfüllen“ von Spalten in einer Textdatei, ähnlich der Excel-Ausfüllfunktion

Befehl zum „Ausfüllen“ von Spalten in einer Textdatei, ähnlich der Excel-Ausfüllfunktion

Ich habe eine Textdatei mit Zeilen und Spalten innerhalb dieser Zeilen. Ich möchte im Wesentlichen die Excel-Funktion „Nach unten ausfüllen“ replizieren. Mit anderen Worten, wenn sich in einer Zeile eine leere „Zelle“ befindet, wird in die Zeile darüber geschaut und der Wert im entsprechenden Feld darüber nach unten ausgefüllt. Beispiel mit „^“ als Spaltentrennzeichen:

London^Paris^Moscow^Berlin
^^Melbourne^New York^Washington
^^^Sydney^Singapore^New Delhi
^^New York^Washington
Kuala Lumpur^Bangkok^Hong Kong
^^^^Johannesburg^Sydney^Singapore^New Delhi
Amsterdam
^^Bucharest

... wird zu (ausgefüllte Elemente zur besseren Übersicht in GROSSBUCHSTABEN):

London^Paris^Moscow^Berlin
LONDON^PARIS^Melbourne^New York^Washington
LONDON^PARIS^MMELBOURNE^Sydney^Singapore^New Delhi
LONDON^PARIS^New York^Washington
Kuala Lumpur^Bangkok^Hong Kong
KUALA LUMPUR^BANGKOK^HONG KONG^^Johannesburg^Sydney^Singapore^New Delhi
Amsterdam
AMSTERDAM^^Bucharest

Die Funktion besteht also im Wesentlichen darin, alle leeren Felder zu identifizieren und, sofern vorhanden, den Wert aus dem entsprechenden Feld darüber nach unten zu ziehen. Es ist wichtig, die Feld-/Spaltentrennzeichen angeben zu können. Irgendwelche Ideen?

Antwort1

awk -F'^' -v OFS='^' \
   '{
        for (i = 1; i <= NF; i++) {
                if ($i == "") $i = save[i]
                else          save[i] = $i
        }
        for (i = NF+1; i <= 99; i++) save[i] = ""
        print
    }'

Dabei wird ein Array verwendet, das aufgerufen wird, save um die Werte von einer Zeile zur nächsten zu speichern (nach unten ausfüllen). Alles darin awkwird implizit auf null initialisiert, sodass das saveArray leer bleibt, bis ihm Daten zugewiesen werden. (Daher bleiben alle leeren Felder in der ersten Zeile leer, da keine vorherigen Daten vorhanden sind, die nach unten kopiert werden können.)

Für jede Zeile

  • Für jedes Feld, das in dieser Zeile ( for (i = 1; i <= NF; i++)) vorhanden ist,
    • Wenn es leer ist, füllen Sie es mit dem gespeicherten (kopierten) Wert für diese Spalte.
    • andernfalls speichern Sie den aktuellen Wert für eine mögliche Verwendung in nachfolgenden Zeilen.
  • Löschen Sie dann das saveArray für alle Spalten, die in der aktuellen Zeile nicht vorhanden sind. Wenn wir beispielsweise zu Zeile 4 gelangen (die nur vier Felder hat), „vergessen“ wir, dass die Spalten 5 und 6 von Zeile 3 „Singapur“ und „Neu-Delhi“ enthielten. Und wenn wir zu Zeile 7 gelangen (die nur ein Feld hat), „vergessen“ wir, dass Spalte 2 von Zeile 5 „Bangkok“ enthielt, sodass es nicht in Zeile 8 eingegeben werden kann (wo Spalte 2 leer ist).

    Ersetzen Sie 99 durch die größte Anzahl von Feldern, die Sie (jemals) in einer Zeile erwarten.

verwandte Informationen