java:type_casting

Differences

This shows you the differences between two versions of the page.

Link to this comparison view

Next revision
Previous revision
Next revision Both sides next revision
java:type_casting [2016/02/12 17:08]
gthanos created
java:type_casting [2016/02/15 08:29]
gthanos [Κριτήρια χρήσης της κληρονομικότητας ως εργαλείο ανάπτυξης λογισμικού]
Line 7: Line 7:
 </​code>​ </​code>​
  
-Από την παραπάνω δήλωση η μεταβλητή ''​myBike''​ είναι τύπου ''​MountainBike''​. Επειδή όμως ο τύπος ''​MountainBike''​ κληρονομεί από την μεταβλητή ''​Bicycle''​ η συγκεκριμένη μεταβλητή είναι και τύπου ​Bicycle. Επομένως θα μπορούσαμε να γράψουμε+Από την παραπάνω δήλωση η μεταβλητή ''​myBike''​ είναι τύπου ''​MountainBike''​. Επειδή όμως ο τύπος ''​MountainBike''​ κληρονομεί από την μεταβλητή ''​Bicycle'' ​**__η συγκεκριμένη μεταβλητή είναι και τύπου ​Bicycle__**. Επομένωςθα μπορούσαμε να γράψουμε
  
 <code java> <code java>
Line 15: Line 15:
 </​code>​ </​code>​
  
-Την παραπάνω ανάθεση την ονομάζουμε //Implicit Casting// διότι αναθέτουμε μία μεταβλητή ενός τύπου δεδομένων (''​myBike''​) σε μία μεταβλητή γονικού τύπου δεδομένων (''​myBicycle''​),​ χωρίς type casting.+Την παραπάνω ανάθεση την ονομάζουμε ​άρρητη μετατροπή (//implicit casting//διότι αναθέτουμε μία μεταβλητή ενός τύπου δεδομένων (''​myBike''​) σε μία μεταβλητή γονικού τύπου δεδομένων (''​myBicycle''​),​ χωρίς ​να ορίζουμε μία μετατροπή τύπου (//type cast//).
  
 Ας δοκιμάσουμε το ανάποδο παράδειγμα τώρα Ας δοκιμάσουμε το ανάποδο παράδειγμα τώρα
Line 24: Line 24:
 </​code>​ </​code>​
  
-Σε αυτή την περίπτωση ο compiler διαμαρτύρεται,​ διότι η μεταβλητή ''​myBicycle''​ είναι τύπου ''​Bicycle''​ και δεν είναι απαραίτητο ότι είναι και τύπου ''​MountainBike''​. Αν θέλουμε να ξεπεράσουμε το παραπάνω ​πρόβλημα θα πρέπει να γράψουμε το εξής:+Σε αυτή την περίπτωση ο compiler διαμαρτύρεται,​ διότι η μεταβλητή ''​myBicycle''​ είναι τύπου ''​Bicycle''​ και δεν είναι απαραίτητο ότι είναι και τύπου ''​MountainBike''​. Αν θέλουμε να ξεπεράσουμε το παραπάνω ​μήνυμα λάθους του compiler ​θα πρέπει να γράψουμε το εξής:
  
 <code java> <code java>
Line 31: Line 31:
 </​code>​ </​code>​
  
-Εδώ ενημερώνουμε τον compiler ότι η μεταβλητή ''​myBicycle''​ είναι και τύπου ''​MountainBike'',​ λαμβάνοντας ο προγραμματιστής την ευθύνη ότι ​κάτι τέτοιο ​ισχύει. Εάν δεν ισχύει ​κάτι τέτοιο ​κατά την εκτέλεση του προγράμματος θα παραχθεί μία εξαίρεση (exception)*. Θα δούμε πιο κάτω τι είναι και πως διαχειριζόμαστε τις εξαιρέσεις.+Εδώ ενημερώνουμε τον compiler ότι η μεταβλητή ''​myBicycle''​ είναι και τύπου ''​MountainBike'',​ λαμβάνοντας ο προγραμματιστής την ευθύνη ότι ​αυτό ισχύει. Εάν δεν ισχύεικατά την εκτέλεση του προγράμματος θα παραχθεί μία εξαίρεση (exception)*. Θα δούμε πιο κάτω τι είναι και πως διαχειριζόμαστε τις εξαιρέσεις.
  
 Ένας πιο ασφαλής τρόπος για να επαναλάβουμε τον παραπάνω κώδικα,​ χωρίς να παραχθεί εξαίρεση είναι ο εξής: Ένας πιο ασφαλής τρόπος για να επαναλάβουμε τον παραπάνω κώδικα,​ χωρίς να παραχθεί εξαίρεση είναι ο εξής:
Line 45: Line 45:
 ===== Κριτήρια χρήσης της κληρονομικότητας ως εργαλείο ανάπτυξης λογισμικού ===== ===== Κριτήρια χρήσης της κληρονομικότητας ως εργαλείο ανάπτυξης λογισμικού =====
  
-Ας επανέλθουμε στο παράδειγμα του ορθογωνίου παραλληλογράμμου το οποίο έχουμε συναντήσει αρκετές φορές στο παρελθόν.+Ας επανέλθουμε στο παράδειγμα του ορθογωνίου παραλληλογράμμου το οποίο έχουμε συναντήσει αρκετές φορές στο παρελθόν ​και ας προσπαθήσουμε να δημιουργήσουμε την κλάση ενός [[wp>​Cuboid|κυβοειδούς]] με χρήση της υφιστάμενης κλάσης του [[java:​class|ορθογωνίου παραλληλογράμμου]].
  
 +Πριν ξεκινήσουμε την υλοποίηση θα πρέπει να αποφασίσουμε εάν θέλουμε να δημιουργήσουμε το κυβοειδές χρησιμοποιώντας ως μεταβλητή της νέας κλάσης ένα αντικείμενο της κλάσης //​Rectangle//​ ή επιθυμούμε να επεκτείνουμε την κλάση //​Rectangle//​ μέσω της νέας κλάσης. Δείτε παρακάτω τις δύο παραλλαγές της κλάσης //Cuboid// με και χωρίς κληρονομικότητα.
  
 +<code java Cuboid.java>​
 +public class Cuboid {
 +  Rectangle rec;
 +  int length;
 +  ​
 +  public Cuboid(int l, int w, int h) {
 +    rec = new Rectangle(w,​h);​
 +    length = l;
 +  }
 +  ​
 +  public int getLength() { return length; }
 +  public void setLength(int l) { length = l; }
 +  ​
 +  public int volume() { return length * rec.area(); }
 +}
 +</​code>​
 +
 +ή 
 +
 +<code java Cuboid.java>​
 +public class Cuboid extends Rectangle {
 +  int length;
 +  ​
 +  public Cuboid(int l, int w, int h) {
 +    super(w,h);
 +    length = l;
 +  }
 +  ​
 +  public int getLength() { return length; }
 +  public void setLength(int l) { length = l; }
 +  ​
 +  public int volume() { return length * area(); }
 +}
 +</​code>​
 +
 +Οι παραπάνω δύο κλάσεις μεταγλωττίζονται και παράγουν το ίδιο λειτουργικό αποτέλεσμα. Το ερώτημα είναι ποια από τις δύο μεθόδους θα προτιμήσουμε. Η απάντηση είναι απλή και συνίσταται στο εξής: Εάν ο νέος τύπος δεδομένων που προκύπτει ανήκει στον τύπο δεδομένων της αρχικής κλάσης τότε μπορούμε να χρησιμοποιήσουμε την κληρονομικότητα ως μέθοδο ανάπτυξης. Εάν όμως ο νέος τύπος δεδομένων δεν αποτελεί τύπο δεδομένων και της παραπάνω κατηγορίας. ​
 +
 +Για παράδειγμα,​ [[java:​inheritance|στο αρχικό παράδειγμα της κληρονομικότητας]],​ από την κλάση Bicycle προκύπτουν οι κλάσεις //​MountainBike//,​ //​RoadBike//​ και //​TandemBike//​. Και οι 3 νέες κλάσεις είναι τύπου Bicycle, καθώς αποτελούν εξειδικεύσεις της γενικής κλάσης του ποδηλάτου. ​
 +
 +Στην περίπτωση που περιγράψαμε παραπάνω κάτι τέτοιο δεν ισχύει. Αν και η κλάση του κυβοειδούς χρειάζεται ένα ορθογώνιο παραλληλόγραμμο για να περιγραφεί,​ το κυβοειδές δεν είναι ορθογώνιο παραλληλόγραμμο. Δεν μπορούμε να πάμε δηλαδή από το κυβοειδές προς το ορθογώνιο παραλληλόγραμμο διατηρώντας τις βασικές ιδιότητες του κυβοειδούς,​ καθώς το κυβοειδές είναι ένα τρισδιάστατο σχήμα, ενώ το ορθογώνιο παραλληλόγραμμο διδιάστατο.
java/type_casting.txt · Last modified: 2017/02/16 13:34 by gthanos