ΛΟΓ102: Τεχνολογία Λογισμικού Ι Διδάσκων: Νίκος Παπασπύρου 1Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Διαφάνειες παρουσίασης #11 4 Διπλά συνδεδεμένες λίστες 4 Δυαδικά δένδρα 4 Διάσχιση δένδρων 4 Παράσταση αριθμητικών εκφράσεων
2Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Διπλά συνδεδεμένες λίστες(i) firstlast u Doubly linked lists u Δυο σύνδεσμοι σε κάθε κόμβο l προς τον επόμενο κόμβο l προς τον προηγούμενο κόμβο
3Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Διπλά συνδεδεμένες λίστες(ii) u Τύπος κόμβου DListNode typedef struct DListNode_tag { int data; struct DListNode_tag * next; struct DListNode_tag * prev; } DListNode; u Τύπος dlist typedef struct { DListNode * first; DListNode * last; } dlist; u Άδεια λίστα const dlist dlistEmpty = { NULL, NULL };
4Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Διπλά συνδεδεμένες λίστες(iii) u Εισαγωγή στοιχείου στην αρχή void dlistInsert (dlist * lp, int t) { DListNode * n = (DListNode *) malloc(sizeof(DListNode)); if (n == NULL) { fprintf(stderr, "Out of memory\n"); exit(1); } n->data = t;
5Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Διπλά συνδεδεμένες λίστες(iv) u Εισαγωγή στοιχείου στην αρχή (συνέχεια) if (lp->first == NULL) { n->prev = n->next = NULL; lp->first = lp->last = n; } else { n->prev = NULL; n->next = lp->first; lp->first->prev = n; lp->first = n; } }
6Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Δυαδικά δένδρα(i) u Binary trees u Δυο σύνδεσμοι σε κάθε κόμβο l αριστερό και δεξί παιδί u Κάθε κόμβος έχει 0, 1 ή 2 παιδιά u Ρίζα: ο αρχικός κόμβος του δένδρου u Φύλλα: κόμβοι χωρίς παιδιά u Βάθος κόμβου: αριθμός συνδέσμων από τη ρίζα
7Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Δυαδικά δένδρα(ii) u Τύπος κόμβου TreeNode typedef struct TreeNode_tag { int data; struct TreeNode_tag * left; struct TreeNode_tag * right; } TreeNode; u Τύπος tree typedef TreeNode * tree; u Κενό δένδρο const tree treeEmpty = NULL;
8Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Δυαδικά δένδρα(iii) u Εισαγωγή σε δένδρα l Καθοριστική απόφαση: σε ποιο σημείο του δένδρου θα εισαχθεί ο νέος κόμβος l Ισοζυγισμένα δένδρα (balanced trees): το βάθος δυο φύλλων διαφέρει το πολύ κατά 1 u Συνάρτηση μέγιστου βάθους int treeDepth (tree t) { if (t == NULL) return 0; return 1 + max(treeDepth(t->left), treeDepth(t->right)); }
9Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Δυαδικά δένδρα(iv) u Εισαγωγή σε ισοζυγισμένα δένδρα void treeBalancedInsert (tree * t, int d) { if (*t == NULL) { *t = (TreeNode *) malloc(sizeof(TreeNode)); if (*t == NULL) { fprintf(stderr, "Out of memory\n"); exit(1); } (*t)->data = d; (*t)->left = (*t)->right = NULL; }
10Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Δυαδικά δένδρα(v) u Εισαγωγή σε ισοζυγισμένα δένδρα (συνέχεια) else { int d1 = treeDepth((*t)->left); int d2 = treeDepth((*t)->right); if (d1 <= d2) treeBalancedInsert( &((*t)->left), d); else treeBalancedInsert( &((*t)->right), d); } }
11Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι u Σειρά με την οποία διασχίζονται οι κόμβοι l κατά βάθος (depth first) l κατά πλάτος (breadth first) Διάσχιση δυαδικών δένδρων(i) u Κατά βάθος 42, 10, 7, 14, 12, 30, 50, 55, 52 u Κατά πλάτος 42, 10, 50, 7, 14, 55, 12, 30, 52
12Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Διάσχιση δυαδικών δένδρων(ii) u Εκτύπωση κατά βάθος l πολύ απλά, με χρήση αναδρομής u Υλοποίηση void treePrintDF (tree t) { if (t != NULL) { printf("%d ", t->data); treePrintDF(t->left); treePrintDF(t->right); } }
13Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Διάσχιση δυαδικών δένδρων(iii) u Εκτύπωση κατά πλάτος l με τη βοήθεια ουράς για την αποθήκευση δεικτών προς τους κόμβους που δεν έχουν επισκεφθεί u Υλοποίηση void treePrintBF (tree t) { queue q = queueEmpty; if (t != NULL) queueInsert(&q, t);
14Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Διάσχιση δυαδικών δένδρων(iv) u Εκτύπωση κατά πλάτος, υλοποίηση (συνέχεια) while (!queueIsEmpty(q)) { TreeNode * n = queueRemove(&q); printf("%d ", n->data); if (n->left != NULL) queueInsert(&q, n->left); if (n->right != NULL) queueInsert(&q, n->right); } }
15Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Αριθμητικές εκφράσεις(i) u Παράδειγμα 3 * (24 / 2) + (9 - 3) u Παράσταση σε μορφή δυαδικού δένδρου l οι αριθμοί στα φύλλα l οι τελεστές στους υπόλοιπους κόμβους + *– / 9 u Διάσχιση κατά βάθος
16Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Αριθμητικές εκφράσεις(ii) u Ενθεματική παράσταση l infix notation l ο τελεστής ανάμεσα στα τελούμενα l διφορούμενη: χρειάζονται παρενθέσεις l η συνήθης μορφή για τον άνθρωπο u Αποτέλεσμα (3 * (24 / 2)) + (9 - 3) + *– / 9
17Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Αριθμητικές εκφράσεις(iii) u Προθεματική παράσταση l prefix notation l ο τελεστής πριν τα τελούμενα l όχι διφορούμενη, δε χρειάζονται παρενθέσεις l απλή μηχανική ανάγνωση u Αποτέλεσμα + * 3 / *– / 9
18Νίκος ΠαπασπύρουΛΟΓ102: Τεχνολογία Λογισμικού Ι Αριθμητικές εκφράσεις(iv) u Επιθεματική παράσταση l postfix notation l ο τελεστής μετά τα τελούμενα l όχι διφορούμενη, δε χρειάζονται παρενθέσεις l απλή μηχανική αποτίμηση u Αποτέλεσμα / * *– / 9