java:super_operator

Differences

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

Link to this comparison view

Both sides previous revision Previous revision
Next revision
Previous revision
java:super_operator [2020/03/27 13:56]
gthanos [Πρόσβαση στους κατασκευαστές της γονικής κλάσης μέσω του τελεστή super]
java:super_operator [2022/03/11 05:25]
gthanos [Πρόσβαση στα πεδία της γονικής κλάσης]
Line 1: Line 1:
 ====== Ο τελεστής super ====== ====== Ο τελεστής super ======
  
-Σε προηγούμενη παράγραφο είδαμε την χρήση του **[[java:this_operator |τελεστή this]]**. Σε αναλογία με τον τελεστή **this**, ο τελεστής **super** δείχνει στο αντικείμενο της γονικής κλάσης. Προϋπόθεση για την χρήση του τελεστή **super** είναι να υφίσταται γονική κλάση μέσω της διαδικασίας της κληρονομικότητας. +Σε προηγούμενη παράγραφο είδαμε την χρήση του **[[java:this_operator |τελεστή this]]**. Σε αναλογία με τον τελεστή **this**, ο τελεστής **super** δείχνει στο αντικείμενο της γονικής κλάσης.  
  
 ===== Πρόσβαση στους κατασκευαστές της γονικής κλάσης μέσω του τελεστή super ===== ===== Πρόσβαση στους κατασκευαστές της γονικής κλάσης μέσω του τελεστή super =====
  
-Λαμβάνοντας κώδικα από το προηγούμενο παράδειγμα του ποδηλάτου έχουμε τις κλάσεις Bicycle και MountainBike.+Επαναλαμβάνοντας τον βασικό κώδικα από το προηγούμενο παράδειγμα του παραλληλογράμμου έχουμε:
  
-<code java Bicycle.java> +<code java BasicRectangle.java> 
-public class Bicycle { +class BasicRectangle {
-         +
-    private int frameSize; +
-    private int gearsNumber; +
-    private String color; +
-        +
-    public Bicycle(int frameSize, int gearsNumber, String color) { +
-        this.frameSize = frameSize; +
-        this.gearsNumber = gearsNumber; +
-        this.color = color; +
-    }+
          
-    public int getFrameSize() { +  int width
-          return frameSize+  int height
-    } +  
-     +  public Rectangle(int initWidth, int initHeight) { 
-    public int getGearsNumber() { +    width = initWidth
-          return gearsNumber+    height initHeight
-    } +  
-     +  
-    public String getColor() { +
-        return color+
-    +
-     +
-    public void setColor(String color) { +
-        this.color color+
-    +
-     +
-    public String toString() { +
-        return "frame: "+frameSize+", gears: "+gearsNumber+", color: "+color; +
-    }+
 } }
 </code> </code>
  
-<code java MountainBike.java> +Η κλάση Rectangle περιέχει ένα πεδίο τύπου Point. Την κλάση Point μπορείτε να την βρείτε [[java:inheritance|εδώ]]. 
-public class MountainBike extends Bicycle { + 
-     +<code java Rectangle.java> 
-    private boolean suspension;+class Rectangle extends BasicRectangle{
          
-    public MountainBike(int frameSize, int gearsNumber, String color, boolean hasSuspension) { +  Point origin;
-        super(frameSize, gearsNumber, color); +
-        this.suspension = hasSuspension; +
-    }+
          
-    public boolean hasSuspension() { +  public Rectangle(int initWidth, int initHeight, Point initOrigin) { 
-        return suspension; +    super(initWidth, initHeight); 
-    +    origin initOrigin
-     +  
-    public void updateColor(String color{ +   
-        //this.color color;  // δεν έχουμε πρόσβαση στο private πεδίο color +  public Rectangle(int initWidth, int initHeight, int originX, int originY) { 
-        setColor(color)+    super(initWidth, initHeight); 
-    +    origin = new Point(originX,originY); 
-     +  } 
-    public String toString() { +  
-        String str = ", hasSuspension: " + (suspension ? "yes" : "no"); +
-        return super.toString() + str+
-    }+
 } }
 </code> </code>
  
-H χρήση του τελεστή **super** χρησιμοποιείται για να προσπελάσει τον κατασκευαστή της γονικής κλάσης και να αρχικοποιήσει τις μεταβλητές που ανήκουν στην κλάση αυτή.+Ο τελεστής **super** χρησιμοποιείται στην υποκλάση για να προσπελάσει τον κατασκευαστή της γονικής κλάσης και να αρχικοποιήσει με αυτό τον τρόπο τις μεταβλητές που ανήκουν στο γονικό κομμάτι της κλάσης. 
 + 
 +Η κλήση του γονικού κατασκευαστή με χρήση της λέξης super πρέπει να βρίσκεται ως πρώτη εντολή στο σώμα κάθε κατασκευαστή.
  
 ==== Σειρά αρχικοποίησης μεταξύ της γονικής και και της απογόνου κλάσης ==== ==== Σειρά αρχικοποίησης μεταξύ της γονικής και και της απογόνου κλάσης ====
  
-Στις περιπτώσεις που μία κλάση είναι απόγονος άλλης κλάσης η διαδικασία αρχικοποίησης έχει ως εξής. Αρχικά αρχικοποιείται το τμήμα της κλάσης που αφορά την γονική κλάση καλώντας των κατασκευαστή αυτής μέσω του τελεστή **super** και στη συνέχεια αρχικοποιείται η απόγονος κλάση. +Στις περιπτώσεις που μία κλάση είναι απόγονος άλλης κλάσης η διαδικασία αρχικοποίησης έχει ως εξής. Αρχικά αρχικοποιείται το τμήμα της κλάσης που αφορά την γονική κλάση καλώντας τον κατασκευαστή αυτής μέσω του τελεστή **super** και στη συνέχεια αρχικοποιείται η απόγονος κλάση. Εάν κατά την κλήση **super** η γονική κλάση έχει με τη σειρά της μία άλλη πρόγονο κλάση, οφείλει να καλέσει τον κατασκευαστή αυτής. Η διαδικασία επαναλαμβάνεται μέχρι να κληθεί ο κατασκευαστής της κλάσης [[https://docs.oracle.com/javase/7/docs/api/java/lang/Object.html|java.lang.Object]].
  
 Εάν δεν υπάρχει κλήση του κατασκευαστή της γονικής κλάσης μέσω του τελεστή **super** στον κατασκευαστή της απογόνου κλάσης, τότε ο compiler αναζητά εάν υπάρχει ο **default** κατασκευαστής για την γονική κλάση (δηλ. κατασκευαστής χωρίς ορίσματα) και καλεί αυτόματα αυτόν. Εάν δεν υπάρχει ούτε **default** κατασκευαστής εμφανίζει μήνυμα λάθους. Εάν δεν υπάρχει κλήση του κατασκευαστή της γονικής κλάσης μέσω του τελεστή **super** στον κατασκευαστή της απογόνου κλάσης, τότε ο compiler αναζητά εάν υπάρχει ο **default** κατασκευαστής για την γονική κλάση (δηλ. κατασκευαστής χωρίς ορίσματα) και καλεί αυτόματα αυτόν. Εάν δεν υπάρχει ούτε **default** κατασκευαστής εμφανίζει μήνυμα λάθους.
Line 109: Line 84:
 ===== Πρόσβαση σε πεδία και μεθόδους των αντικειμένων της γονικής κλάσης μέσω του τελεστή super ===== ===== Πρόσβαση σε πεδία και μεθόδους των αντικειμένων της γονικής κλάσης μέσω του τελεστή super =====
  
-Στο παρακάτω παράδειγμα, παρατηρήστε την χρήση του τελεστή **super** προκειμένου να προσπελάσετε τη μέθοδο **//toString//** της γονικής κλάσης.+==== Πρόσβαση στις μεθόδους της γονικής κλάσης ====
  
-<code java KittenBirth.java+Ξαναγράφουμε τις κλάσεις ''BasicRectangle'' και ''Rectangle'', προσθέτοντας αυτή τη φορά τον ορισμό της μεθόδου ''public String toString()'' και στις δύο. Η μέθοδος αυτή, όπως έχουμε δει, είναι υπαρκτή σε όλα τα αντικείμενα διότι περιέχεται στην κλάση [[https://docs.oracle.com/javase/7/docs/api/java/lang/Object.html|java.lang.Object]].
-class Mammal {+
  
 +<code java BasicRectangle.java>
 +class BasicRectangle {
 +    
 +  int width;
 +  int height;
 + 
 +  public Rectangle(int initWidth, int initHeight) {
 +    width = initWidth;
 +    height = initHeight;
 +  }
 +  
   public String toString() {   public String toString() {
-    return "I am a mammal.";+    return "width: "+width+", height: "+height;
   }   }
 } }
 +</code>
  
-class Cat extends Mammal {+<code java Rectangle.java> 
 +class Rectangle extends BasicRectangle{ 
 +     
 +  Point origin; 
 +     
 +  public Rectangle(int initWidth, int initHeight, Point initOrigin) { 
 +    super(initWidth, initHeight); 
 +    origin = initOrigin; 
 +  } 
 +   
 +  public Rectangle(int initWidth, int initHeight, int originX, int originY) { 
 +    super(initWidth, initHeight); 
 +    origin = new Point(originX,originY); 
 +  } 
 +  
   public String toString() {   public String toString() {
-    return super.toString() + " In particular, I am a cat.";+    return origin.toString() + " " + super.toString();
   }   }
-+   
- +  public int area() { 
-public class KittenBirth { +    return width*height;
-  public static void main(String []args) { +
-    Cat kitten = new Cat(); +
-    System.out.println(kitten);+
   }   }
 } }
 </code> </code>
  
-Αντίστοιχα, ο κατασκευαστής της κλάσης ''MountainBike'' θα μπορούσε να γραφεί ως εξής εάν τα πεδία cadencegear και speed δεν ήταν δηλωμένα private.+Παρατηρήστε ότι η μέθοδος toString για την κλάση Rectangle χρησιμοποιεί τη μέθοδο toString της κλάσης ''Point'' και της γονικής της κλάσης ''BasicRectangle'' (βλέπε ''super.toString()''). Ο λόγος που σε αυτό το σημείο είναι απαραίτητη η χρήση του τελεστή **super**, είναι ότι εάν δεν βάλουμε τη λέξη **super.** κατά την κλήση της toString(), η συνάρτηση δεν θα καλέσει τη συνάρτηση toString της γονικής κλάσης, αλλά τον εαυτό της. Σε αυτή την περίπτωσηη αναδρομική κλήση είναι ατέρμονη, μοιραία θα οδηγήσει σε υπέρβαση της διαθέσιμης στοίβας εκτέλεσης του προγράμματος, με συνέπεια τον τερματισμό του.
  
-<code java MountainBike.java> +==== Πρόσβαση στα πεδία της γονικής κλάσης ==== 
-public class MountainBike extends Bicycle { + 
-  +Επιπλέονστην κλάση Rectangleορίσαμε παραπάνω τη μέθοδο area. H μέθοδος μπορεί να γραφεί με τις εξής τρεις (3ισοδύναμες παραλλαγές
-    // the MountainBike subclass has +<code java>  
-    // one field +  public int area() { 
-    public int seatHeight; +    return width * height
-  +  }
-    // the MountainBike subclass has +
-    // one constructor +
-    public MountainBike(int startHeightint startCadence, +
-                        int startSpeed, int startGear) { +
-        //super(startCadence, startSpeed, startGear)+
-        super.cadence = startCadence; +
-        super.speed = startSpeed; +
-        super.gear = startGear; +
-        seatHeight = startHeight; +
-    }    +
-  +
-    // the MountainBike subclass has +
-    // one method +
-    public void setHeight(int newValue) { +
-        seatHeight = newValue+
-       +
-  +
-}+
 </code> </code>
 +<code java> 
 +  public int area() {
 +    return this.width * this.height;
 +  }
 +</code>
 +<code java> 
 +  public int area() {
 +    return super.width * super.height;
 +  }
 +</code>
 +
 +Ο λόγος που μπορούμε να γράψουμε τη συνάρτηση με τους δύο παραπάνω τρόπους είναι ότι το πεδίο width, που κληρονομείται από τη γονική κλάση, ανήκει τόσο στην τρέχουσα κλάση ''Rectangle'', όσο και στη γονική της ''BasicRectangle''.
  
-Συμπερασματικά, ο τελεστής **super** δείχνει στο αντικείμενο της γονικής κλάσης και χρησιμοποιείται για να προσπελαστούν δεδομένα ή μεταβλητές που ανήκουν στο τμήμα του τρέχοντος αντικειμένου που αφορά την γονική κλάση+Συμπερασματικά, ο τελεστής **super** δείχνει στο τμήμα του τρέχοντος αντικειμένου που αφορά τη γονική κλάση και χρησιμοποιείται για να προσπελαστούν πεδία ή μέθοδοι που ανήκουν σε αυτό
  
 <WRAP important 80% center round>Απαραίτητη προϋπόθεση για την πρόσβαση στα πεδία της γονικής κλάσης μέσω του τελεστη **super** είναι η κλάση να έχει πρόσβαση στα δεδομένα ή τις μεθόδους της γονικής κλάσης τις οποίες καλείται να προσπελάσει. Για να γίνει αυτό, τα πεδία και οι μέθοδοι της γονικής κλάσης που θέλουμε να προσπελάσουμε ΔΕΝ θα πρέπει **α)** να έχουν προσδιοριστή πρόσβασης **private** ή **β)** δεν θα πρέπει να έχουν προσδιοριστή **package private (δηλ. κανένα προσδιοριστή)** και να ανήκουν σε διαφορετικά πακέτα.  <WRAP important 80% center round>Απαραίτητη προϋπόθεση για την πρόσβαση στα πεδία της γονικής κλάσης μέσω του τελεστη **super** είναι η κλάση να έχει πρόσβαση στα δεδομένα ή τις μεθόδους της γονικής κλάσης τις οποίες καλείται να προσπελάσει. Για να γίνει αυτό, τα πεδία και οι μέθοδοι της γονικής κλάσης που θέλουμε να προσπελάσουμε ΔΕΝ θα πρέπει **α)** να έχουν προσδιοριστή πρόσβασης **private** ή **β)** δεν θα πρέπει να έχουν προσδιοριστή **package private (δηλ. κανένα προσδιοριστή)** και να ανήκουν σε διαφορετικά πακέτα. 
java/super_operator.txt · Last modified: 2022/03/11 05:25 by gthanos