8. Πίνακες και αλφαριθμητικά

Ένας πίνακας είναι ένα σύνολο δεδομένων ενός τύπου, οργανωμένα κάτω από ένα κοινό όνομα. Για να αναφερθούμε σε μια τιμή του πίνακα ένας δείκτης χρησιμοποιείται. Οι δείκτες που αναφέρονται σε ένα πίνακα ξεκινούν από τον αριθμό μηδέν. Παράδειγμα: Θέλουμε να αποθηκεύσουμε τις τιμές θερμοκρασίας για κάθε μια από τις τελευταίες έξι ώρες. Δηλώνουμε τον πίνακα των έξι τιμών τύπου float ως εξής:

float temperature[6];

Εκχωρούμε σε κάθε θέση του πίνακα τις έξι τιμές της θερμοκρασίας ως εξής:

temperature[0] = 22.3;
temperature[1] = 16.7;
temperature[2] = 21.2;
temperature[3] = 25.0;
temperature[4] = 27.3;
temperature[5] = 26.2;

Για να αποφύγουμε αυτή την επίπονη εργασία, θα μπορούσαμε να ορίσουμε τον πίνακα και ταυτόχρονα να του εκχωρήσουμε τις τιμές σε μια πρόταση ως εξής:

float temperature[6] = {22.3, 16.7, 21.2, 25.0, 27.3, 26.2};

Την τιμή σε μια θέση του πίνακα μπορούμε να την χρησιμοποιήσουμε όπως οι συνηθισμένες μεταβλητές, για παράδειγμα η τελευταία τιμή του πίνακα αναφέρεται ως temperature[5] και έχει τιμή 26.2 ενώ η πρώτη τιμή αναφέρεται ως temperature[0] και παίρνει τιμή 22.3

Ως παράδειγμα ας υπολογίσουμε τη μέση τιμή της θερμοκρασίας με το ακόλουθο απόσπασμα κώδικα:

float sum = 0, temp;
int s = sizeof(temperature);
for(int k =0; k<s; k++) sum+=temperature[k];
temp = sum / s;

Στον κώδικα αυτό χρησιμοποιούμε τον βρόγχο for για να αναφερθούμε σε κάθε μια και σε όλες τις τιμές της θερμοκρασίας.

Δουλεύοντας με τα strings

Μια από τις πιο ιδιόμορφες πτυχές της γλώσσας C είναι δουλεύοντας με κείμενο. Δυστυχώς η γλώσσα C χρησιμοποιεί ένα σύνθετο τρόπο για να χειριστεί κείμενο κάτι που θα δυσκολέψει τους αρχάριους. Ευτυχώς οι δημιουργοί του Arduino δημιούργησαν την γλώσσα προγραμματισμού για το Arduino τέτοια που να χειρίζεται το κείμενο σαν αντικείμενα (Strings) κάνοντας τη δουλειά του προγραμματιστή πιο εύκολη. Σε αυτό το κεφάλαιο θα δούμε πως η γλώσσα C χειρίζεται το κείμενο και μετά θα δούμε τον πιο εύκολο τρόπο να δουλεύουμε με κείμενο στο περιβάλλον Arduino.

Για να γεφυρώσουν οι προγραμματιστές το χάσμα των υπολογιστών που βασίζονται στους δυαδικούς αριθμούς και του ανθρώπου που επικοινωνεί με κείμενο, δημιουργήθηκε ένας νέος τύπος δεδομένων ο character data type. Αυτός ο τύπος δεδομένων αποθηκεύει γράμματα, αριθμούς και σύμβολα σε μεταβλητές τύπου char. Παράδειγμα: Για να αποθηκεύσουμε ένα χαρακτήρα στη μνήμη (εδώ τον χαρακτήρα a) θα χρησιμοποιήσουμε τον τύπο δεδομένων character

char letter = ‘a’;

Με την προηγούμενη εντολή το Arduino, αποθηκεύει την ASCII τιμή που αντιπροσωπεύει τον χαρακτήρα ‘a’ στην μεταβλητή letter τύπου char. Όταν ανακτούμε την τιμή της μεταβλητής letter και την χρησιμοποιούμε μέσα στη συνάρτηση Serial.print(letter); το Arduino εμφανίζει τον χαρακτήρα με κωδικό ASCII όπως αντιπροσωπεύει η μεταβλητή letter. Αν είχαμε ορίσει τη μεταβλητή letter με άλλο τύπο π.χ. int κατά την αποστολή στο Serial Monitor θα εκτυπωνόταν η ASCII τιμή του χαρακτήρα αντί για τον χαρακτήρα καθεαυτό.

Ένα C – style string είναι ένα αλφαριθμητικό κείμενο όπου ο κάθε χαρακτήρας είναι δεδομένο τύπου char και είναι τοποθετημένος διαδοχικά στη μνήμη. Τα C – style strings είναι στην ουσία πίνακες χαρακτήρων όπως τους παρουσιάσαμε σε προηγούμενη ενότητα. Μπορούμε να δημιουργήσουμε ένα πίνακα χαρακτήρων με διάφορους τρόπους. Ο κλασσικός τρόπος για να ορίσουμε το C – style string είναι ο εξής:

char test[7] = {‘A’, ‘ ‘, ‘t’, ‘e’, ‘s’, ‘t’, ‘\0’};

Ας σημειώσουμε ότι κάθε χαρακτήρας (συμπεριλαμβανομένου του κενού) είναι ο τύπος δεδομένων char. Επίσης το μέγεθος του πίνακα που δηλώνουμε πρέπει να είναι μεγάλο ώστε να χωρά όλους τους χαρακτήρες συν τον τελικό null χαρακτήρα ‘\0’. Για να χρησιμοποιήσουμε αυτό τον πίνακα χαρακτήρων απλά αναφερόμαστε στο όνομα του.

Serial.println(test);

Στην παραπάνω εντολή το Arduino καταλαβαίνει το τέλος του string με τον χαρακτήρα null δηλαδή τον ‘\0’. Οι δημιουργοί της γλώσσας C δημιούργησαν ένα πιο εύκολα τρόπο εκχώρησης string σε πίνακα χαρακτήρων, απλά εισάγοντας ολόκληρο το κείμενο σε διπλά εισαγωγικά:

char test[15] = “This is a test”;

Ο compiler ξέρει να δημιουργήσει τον πίνακα χαρακτήρων και να εκχωρήσει το κείμενο που δίνεται σε διπλά εισαγωγικά και αυτόματα προσθέτει τον null χαρακτήρα στη τελευταία θέση.

Μερικοί C compilers συμπεριλαμβανομένου αυτού που χρησιμοποιεί το Arduino δημιουργεί τον πίνακα χαρακτήρων χωρίς να δηλώσουμε το μέγεθος του πίνακα. Ο compiler δεσμεύει αρκετό χώρο στη μνήμη για να αποθηκεύσει το κείμενο και τον τελικό χαρακτήρα null τον οποίο εκχωρεί αυτόματα:

char test[] = “Testing the Arduino string”;

Εισαγωγή στα αντικείμενα String

Θεωρώντας το κείμενο στη γλώσσα C ως πίνακα χαρακτήρων, δεν είναι κι ότι καλύτερο, κάτι που οδηγεί σε προβλήματα αν δεν είμαστε προσεκτικοί.

Οι δημιουργοί της γλώσσας προγραμματισμού Arduino ανέπτυξαν ένα νέο τρόπο χειρισμού strings με πολλά πλεονεκτήματα. Συγκεκριμένα δημιούργησαν μια κλάση όπου κάθε string είναι ένα αντικείμενο αυτής της κλάσης. Με αυτό τον τρόπο πολλές λειτουργίες γίνονται στο παρασκήνιο παρέχοντας μεγάλη ευκολία στον προγραμματιστή.

Η κλάση String της γλώσσας Arduino επιτρέπει την εύκολη δημιουργία και εργασία σε κάθε τύπου string, σε αντίθεση με τους C – style character arrays. Ο ευκολότερος τρόπος για να δημιουργήσουμε ένα αντικείμενο String είναι να δηλώσουμε μια μεταβλητή χρησιμοποιώντας τον τύπο δεδομένων String και εκχωρώντας σ’ αυτή μια αλφαριθμητική τιμή:

String test1 = “This is a test string”;

Η κλάση String έχει μια συνάρτηση δημιουργίας (constructor) με όνομα String η οποία μπορεί να μετατρέψει όλους τους τύπους δεδομένων σε ένα αντικείμενο String.

String test2 = String(‘a’);
String test3 = String(“This is a string of characters”);
String test4 = String(31);
String test5 = String(20, HEX);

Το αποτέλεσμα των δηλώσεων αυτών είναι η δημιουργία ενός αντικειμένου String. Το τελευταίο παράδειγμα ορίζει την βάση της αριθμητικής τιμής, εδώ HEX για τον αριθμό που ορίζεται στην πρώτη παράμετρο.

Η διαφορά ορισμού με τον C – style τρόπο είναι ότι δεν ανησυχούμε για το μέγεθος του πίνακα χαρακτήρων. Για παράδειγμα μπορούμε να γράψουμε:

String string1 = “test”;
string1 = “a new test”;

Ένας τρόπος με τον οποίο δουλεύουμε τα sting φαίνεται στο ακόλουθο παράδειγμα:

void setup() {
     Serial.begin(9600);
     String str1 = “This is a test”;
     String str2 = String(“This is a second string”);
     String str3;
     Serial.println(str1);
     str1 = “This is a longer string value";
     Serial.println(str1);
     str1 = String(str1 + “ with more text”);
     Serial.println(str1);
     Serial.println(str2);
     str3 = String(str1 + str2);
     Serial.println(str3);
}
void loop() {
}