Εργαστήριο Λειτουργικών Συστημάτων Φροντιστήριο 3– sed και awk Ντίρλης Νικόλαος
Γρήγορη Επανάληψη Χρησιμοποιουμε το επιθεμα “>” για την προωθηση σε καποιο αρχειο Χρησιμοποιουμε το επιθεμα “<“ για την προωθηση ενος αρχειου ως εισοδο Χρησιμοποιουμε το επιθεμα “|” για να προωθησουμε την εξοδο μιας εντολης στην εισοδο μιας αλλης Μπορουμε να εκτελεσουμε εντολες σειριακα διαχωριζοντας τις εντολες με “;” Μπορουμε να εκτελεσουμε εντολες παραλληλα διαχωριζοντας τις εντολες με “&”
sed και awk sed is a stream editor. A stream editor is used to perform basic text transformations on an input stream Awk is an interpreted programming language designed for text processing and typically used as a data extraction and reporting tool. awk ‘BEGIN { print “Hello World” } ‘
Comma Separated Values file (CSV) Τα αρχεία CSV είναι αρχεία απλού κειμένου (plain text) που αποτελούνται από εγγραφές (records) διαχωριζόμενες μεταξύ τους με line breaks. Η κάθε εγγραφή σε ένα CSV αποτελείται από πεδία (fields) που διαχωρίζονται μεταξύ τους με κόμμα (“,”) ή κάποιον άλλο χαρακτήρα ( πχ tab) διαφορετικό όμως από line break. Τα CSV αρχεία χρησιμοποιούνται ευρέως σε πλήθος εμπορικών και επιστημονικών εφαρμογών.
The “EOL – Problem” Όπως είπαμε, σε ένα CSV έχουμε εγγραφές που διαχωρίζονται μεταξύ τους με line breaks ή διαφορετικά με χαρακτήρες EOL (End Of Line). Σε διαφορετικά λειτουργικά συστήματα οι χαρακτήρες EOL μπορεί να διαφέρουν και έτσι να δημιουργείται πρόβλημα για παράδειγμα αν θέλουμε να κάνουμε compile ένα αρχείο με κώδικα γραμμένο σε Notepad++ σε περιβάλλον Windows σε ένα περιβάλλον Unix. Το πρόβλημα αυτό μπορεί να ξεπεραστεί με πολλούς τρόπους. Για παράδειγμα με την εντολή dos2unix ( ή unix2dos) σε Unix ή χρησιμοποιώντας κάποιες δυνατότητες που μας δίνουν editors ( όπως το Notepad++) να αποθηκεύσουμε το κείμενό μας σε περιβάλλον διαφορετικού ΛΣ από αυτού που τρέχουμε τον editor.
The “EOL – Problem” με χρήση awk Μπορούμε να χρησιμοποιήσουμε και sed ή awk για να λύσουμε το EOL-Problem: # UNIX to DOS (adding CRs on Linux and BSD based OS that haven't GNU extensions) $ awk '{sub("$","\r\n"); printf("%s",$0);}' inputfile > outputfile # DOS to UNIX (removing CRs on Linux and BSD based OS that haven't GNU extensions) $ awk '{gsub("\r",""); print;}' inputfile > outputfile
The “EOL – Problem” με χρήση sed # UNIX to DOS (adding CRs on Linux based OS that use GNU extensions) $ sed -e 's/$/\r/' inputfile > outputfile # DOS to UNIX (removing CRs on Linux based OS that use GNU extensions) $ sed -e 's/\r$//' inputfile > outputfile Φυσικά και άλλες λύσεις είναι πιθανές, όπως η χρησιμοποίηση perl: $ perl -pe 's/\r?\n|\r/\r\n/g' inputfile > outputfile # Convert to DOS $ perl -pe 's/\r?\n|\r/\n/g' inputfile > outputfile # Convert to UNIX $ perl -pe 's/\r?\n|\r/\r/g' inputfile > outputfile # Convert to old Mac
Επεξεργασία CSV με χρήση sed/awk (1) Έστω ότι έχουμε το παρακάτω CSV που ονομάζεται grades.txt το οποίο περιέχει ονόματα φοιτητών με το ΑΜ τους και τον βαθμό τους σε ένα συγκεκριμένο μάθημα : 6945,Christian Novack,4 6946,Esmeralda Coman,7 6947,Tanisha Acoff,6 6948,Carlene Tejera,8 6949,Guy Hinchman,1 6950,Allan Munyon,2 6951,Darcy Magallan,2 6952,Cody Ruud,7 6953,Clinton Bonneau,9 6954,Julio Kieser,2 6955,Nita Klemme,3
Επεξεργασία CSV με χρήση sed/awk (2) Ας θεωρήσουμε πως θέλουμε να κάνουμε μια σειρά αλλαγών στο αρχείο αυτό. Έστω πως θέλουμε να αλλάξουμε το τρίτο όρισμα που είναι ο βαθμός. Ενδεικτικά ο ψευδοκώδικας για κάτι τέτοιο θα ήταν : Διάβασε "Enter student's AM: " am Διάβασε "Enter the new grade of student with $am: " new_grade old= παλιός βαθμός φοιτητή // με grep βρίσκω το record στο CSV και με awk το σωστό field Εκτύπωσε "The previous grade was: " $old sed – Βάλε τα νέα δεδομένα στο σωστό field Εκτύπωσε "Updated students data: "
Επεξεργασία CSV με χρήση sed/awk (3) Απλή εκτύπωση στοιχείων ( πχ ΑΜ φοιτητή ): Διάβασε "Enter a students AM: " am Εκτύπωσε "Students data:" // με cat στο αρχείο και grep ^$am
Επεξεργασία CSV με χρήση sed/awk (4) Αποθήκευση σε νέο αρχείο Διάβασε "Enter a path, to save the file: " NEWPATH Αν [ "$NEWPATH" == "" ] ; Τότε Αποθήκευσε // με τη βοήθεια της sed Αλλιώς export NEWPATH Τέλος _ Αν