Bash | Sortieren (hoch/niedrig) von Werten

  • Hallo,


    ich habe eine CSV-Datei mit 5 Werten pro Zeile und insgesamt 30 Zeilen.


    Beispiel:

    Code
    Wert1,Wert2,Wert3,Wert4,Wert5
    20,17,33,112,18
    21,18,32,118,18
    22,17,33,122,17
    21,16,34,131,18
    19,15,35,134,19
    usw.

    Wie kann ich z.B. von Wert2 den niedrigsten und höchsten Wert herausbekommen?


    Bei Dateien, die nur einen Wert pro Zeile haben, ist das mit sort und tail recht einfach durchzuführen. Aber hier sitzt der Wert2 mittendrin.

    Viele Grüße,

    Peter

  • //Edit// zu lahm.

    Und mich bestraft das Leben ;( ... :lol:

    "Really, I'm not out to destroy Microsoft. That will just be a completely unintentional side effect."

    Linus Benedict Torvalds, 28.9.2003


    Hast Du die Woche schon Deine Raspberry gesichert :fies: Bei mir tut das raspiBackup automatisch :shy:

  • Das mit den hohen und tiefen Werten klappt wunderbar.


    Nun bin ich auf das nächste Problem gestoßen. Ich würde gerne für einen Wert in einer CSV-Datei den Durchschnitt ausrechnen lassen.


    Das ist meine Codezeile:

    Code
    echo $(bc -l <<< "scale=1; ($(cat "daten.csv" | awk -F',' '{sum+=$1}END{print sum}')/$(cat "daten.csv" | wc -l))")

    Mit cat hole ich den Inhalt, schicke ihn zu awk, der eine Summe daraus bildet und mit bc teile ich das durch die Anzahl der Zeilen.


    Grundsätzlich klappt das. Aber awk frisst mir die Werte hinter dem Komma (hier Punkt). Bei der ersten Spalte rechnet er 33+33+33+33+33, somit Durchschnitt 33.


    Irgendwelche Ideen?


    Beispielinhalt der daten.csv:

    Code
    33.2,26.7,29.9
    33.3,26.8,30.4
    33.4,26.9,30.3
    33.6,27.1,30.4
    33.9,27.4,31.1
    usw.

    Viele Grüße,

    Peter

  • Nachtrag:

    Ich bin gerade darauf gestoßen, dass awk sich am Punkt stoßen könnte.


    Als erste Notlösung habe ich mit tr das Kommas in Semikolons ersetzt, sowie dann die Punkte in Kommas, nach dem awk wiederum alles zurück.

    Code
    echo $(bc -l <<< "scale=1; ($(cat "daten.csv" | tr "," ";" | tr "." "," | awk -F',' '{sum+=$1}END{print sum}' | tr "," "." | tr ";" ",")/$(cat "daten.csv" | wc -l))")

    Das sieht schon sehr verwegen aus. *lach*


    Gibt es eine elegantere Lösung?

    Viele Grüße,

    Peter

    Edited once, last by Peter0311 ().

  • Code
    awk -F',' 'BEGIN {min = 9999} NR > 1 {++count;value = $2;sum += value; if(value < min){min = value} if( value > max){max=value;}} END { print min " " max " " sum / count }' inputfile

    Alles auf einer Zeile!


    Man kann es auch auf mehrere Zeilen schreiben, aber dann muss man beim Quoting aufpassen.


    - - - - -


    awk sieht Punkte als Dezimaltrenner das ist problemlos.


    Die Kommandozeile nimmt an dass das File einen Header hat. Falls das nicht der Fall ist NR > 1 loeschen

  • Hier die huebsche Version:


    describe:


    Und der Aufruf davon:

    Code
    awk -F',' -f describe inputfile
  • Die awk Loesung ist definitiv die kuerzeste und lesbarste Version :thumbup: . Aber Ihr kennt mich ja: Ich nutze gerne bash :shy: . Anbei meine Loesung wie ich es in bash schreiben wuerde:

    Code
    ./csv.sh csv.dat 
    Sum:454.4 Cnt:15 Avg:30.2

    "Really, I'm not out to destroy Microsoft. That will just be a completely unintentional side effect."

    Linus Benedict Torvalds, 28.9.2003


    Hast Du die Woche schon Deine Raspberry gesichert :fies: Bei mir tut das raspiBackup automatisch :shy:

  • > Die awk Loesung ist definitiv die kuerzeste und lesbarste Version

    Noeh:


    Code
    python3 -c 'import pandas as pd; print( pd.read_csv("input.csv",header=None)[1].describe() )'

    Und wenn er wirklich nur den Mittelwert will und einen Header hat, wird es noch klarer:

    Code
     python3 -c 'import pandas as pd; print( pd.read_csv("input.csv")["Wert2"].mean() )'

    Edited 2 times, last by Tell ().

  • Eine Library zu nutzen verkürzt natürlich alles sehr und ist unfair :no_sad::) Hier geht es um native Implementierungen ohne Libs ;)

    "Really, I'm not out to destroy Microsoft. That will just be a completely unintentional side effect."

    Linus Benedict Torvalds, 28.9.2003


    Hast Du die Woche schon Deine Raspberry gesichert :fies: Bei mir tut das raspiBackup automatisch :shy:

  • Eine Library zu nutzen verkürzt natürlich alles sehr und ist unfair

    awk ist auch nur ein Programm, dass mit der Bash genutzt wird.

    Für Python gibt es auch ein csv-Modul, dass mit in der Standardbibliothek enthalten ist.


    Wenn man Python anwendet, will man sich eigentlich wohlfühlen und schönen Code sehen.

    One-Liner sind nicht so schön.


    Hier mal mein Versuch mit CSV:


    Soll aber keine Bekehrung zu Python sein, sondern nur aufzeigen, dass die Datenverarbeitung mit Python einfacher ist.

    Wenn man dann noch Pandas lernt, kann man quasi zaubern (z.B. CSV direkt aus dem Internet herunterladen und öffnen mit einer Funktion).

  • Wenn man Python anwendet, will man sich eigentlich wohlfühlen und schönen Code sehen.

    Verstehe mich nicht falsch. Ich bin da ganz bei Dir. Ich habe auch lange genug in Python programmiert. Python ist wesentlich maechtiger als bash. Ich will hier auch keine Diskussion bash vs Python anzetteln. Eine jede Programmiersprache hat seine Staerken und EInsatzgebiete. Und man kann auch mit jeder Programmiersprache ein endliches Problem loesen - und wenn es Assembler oder die Touringmaschine ist :lol:


    Der TE hat bash genutzt weil er sich damit offensichtlich auskennt. Jetzt awk zu nutzen mag fuer ihn schon ein gewisser Quantensprung sein. awk ist eben anders als bash. Ich wollte einfach dem TE nur zeigen wie man es auch in bash hinbekommen kann :)

    "Really, I'm not out to destroy Microsoft. That will just be a completely unintentional side effect."

    Linus Benedict Torvalds, 28.9.2003


    Hast Du die Woche schon Deine Raspberry gesichert :fies: Bei mir tut das raspiBackup automatisch :shy:

  • Ich wollte einfach dem TE nur zeigen wie man es auch in bash hinbekommen kann

    Threadüberschrift ist

    Quote

    Bash | Sortieren (hoch/niedrig) von Werten

    Wenn einer ein günstiges Fahrrad sucht gebe ich ja auch keinen Tipp, wo er ein günstiges Auto bekommt.


    :2cents:

  • Wenn man nur einen Hammer hat, dann ist jedes Problem ein Nagel.

    Klar, man kann sich selbst zwingen, alle Probleme mit einem Hammer zu lösen.


    Genau das ist der Grund, wieso es viele Sprachen gibt.

    Was ist an dem Hinweis und einem passenden Beispiel falsch?

  • Was ist an dem Hinweis und einem passenden Beispiel falsch?

    Falsch ist daran gar nichts

    Wenn der TE aber gerade dabei ist, die Problematik mit bash zu lösen, weil er da vielleicht ein paar Vorkenntnisse hat, verwirrt ihn der Rest womöglich.

  • Was ist an dem Hinweis und einem passenden Beispiel falsch?

    Nichts :) . Vielleicht will der TE ja noch Python lernen oder kennt es schon etwas. So wie ich dem TE zeigen will wie es in bash geht zeigst Du wie es in Python ohne mächtigen Libeinsatz geht :thumbup:

    "Really, I'm not out to destroy Microsoft. That will just be a completely unintentional side effect."

    Linus Benedict Torvalds, 28.9.2003


    Hast Du die Woche schon Deine Raspberry gesichert :fies: Bei mir tut das raspiBackup automatisch :shy: