java:generic_bounded_types

Differences

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

Link to this comparison view

Next revision
Previous revision
java:generic_bounded_types [2015/03/15 21:08]
gthanos created
java:generic_bounded_types [2016/02/26 11:15] (current)
Line 1: Line 1:
-====== ​Κληρονομικότητα ​παραμετρικών τύπων δεδομένων ======+====== ​Φραγμένοι παραμετρικοί τύπων δεδομένων ====== 
 + 
 +===== Άνω φραγμένοι παραμετρικοί τύποι (Upper Bounded Wildcards) ​=====
  
 <code java> <code java>
-public void boxTest(Box<​Number> ​n) { /* ... */ }  //line 1+public ​static ​void process(List<? extends ​Number> ​list) { /* ... */ } 
 +</code>
  
-Box<Number> box = new Box<Number>();  //line 3 +Στην παραπάνω δήλωση ο τύπος δεδομένων της παραμετρικής κλάσης ''​List''​ μπορεί να είναι η κλάση ''​Number''​ η οποιαδήποτε υποκλάση της ''​Number'' ​(π.χ ''​Integer'',​ ''​Double'',​ ''​Float''​).
-box.add(new ​Integer(10));             //​line 4 +
-box.add(new Double(10.1)); ​           //line 5+
  
-Box<​Double>​ doubleBox ​new Box<​Double>​(); // line 7 +===== Κάτω φραγμένοι παραμετρικοί τύποι ​(Lower Bounded Wildcards=====
-doubleBox.add(new Double(10.1)); ​          // line 8+
  
-box.boxTest(doubleBox); // μπορούμε να γράψουμε?​+<code java> 
 +public static void addNumbers(List<?​ super Integer> list) { 
 +    for (int i = 1; i <= 10; i++) { 
 +        list.add(i); 
 +    } 
 +}
 </​code>​ </​code>​
-Ο παραπάνω ​κώδικας είναι σωστός στις γραμμές 3-5 διότι οι κλάσεις ''​Integer''​ και ''​Double''​ είναι υποκλάσεις της κλάσης ''​Number''​. Δεν ισχύει όμως το ίδιο ​για την ​γραμμή 8 καθώς η κλάση ''​Box<Double>'' ​δεν είναι υποκλάση της ​κλάσης ''​Box<​Number>​'',​ όπως δείχνει το παρακάτω σχήμα. + 
-{{:java:generics_inheritance1.png|}}+Στην ​παραπάνω δήλωση ο τύπος δεδομένων της παραμετρικής κλάσης ''​List''​ μπορεί να είναι ​η κλάση ''​Integer''​ ή οποιαδήποτε υπερ-κλάση της ''​Integer''​ (π.χ ''​Number''​). 
 + 
 +===== Μη φραγμένοι παραμετρικοί τύποι (Unbounded Wildcards) ===== 
 + 
 +Ας εξετάσουμε τους μη φραγμένους παραμετρικούς τύπους ​μέσα το παρακάτω παράδειγμα. 
 +<code java> 
 +public static void printList(List<​Object>​ list) { 
 +    for (Object elem : list) 
 +        System.out.println(elem + " "); 
 +    System.out.println();​ 
 +
 +</​code>​ 
 + 
 +Ο παραπάνω κώδικας τυπώνει αντικείμενα από μία λίστα αντικειμένων τύπου ''​Οbject''​. Λόγω των περιορισμών στην ​κληρονομικότητα που ​είδαμε προηγούμενα ο ίδιος κώδικας δεν μπορεί να χρησιμοποιηθεί για να τυπώσει αντικείμενα τύπου ​''​List<​String>''​ ή ''​List<​Integer>''​ καθώς δεν μπορούμε να τοποθετήσουμε στην παράμετρο ​''​List<​Object>​'' ​ένα αντικείμενο άλλης κλάσης. Κατά συνέπεια θα χρειαστούμε ένα άλλο τρόπο γραφής της συγκεκριμένης κλάσης,​ ώστε να απαντά στην γενικότητα. 
 + 
 +Αν θέλουμε να γράψουμε μία αρκετά γενική μέθοδο λίστας που να τυπώνει λίστες οποιουδήποτε αντικειμένου αρκεί να γράψετε το παρακάτω 
 + 
 +<code java> 
 +public static void printList(List<?>​ list) { 
 +    for (Object elem: list) 
 +        System.out.print(elem + " "); 
 +    System.out.println();​ 
 +
 +</​code>​ 
 + 
 +Αντίστοιχα,​ αν θέλουμε να γράψουμε μία μέθοδο που να τυπώνει μόνο αριθμούς (υποκλάσεις της ​//​abstract// ​κλάσης ''​Number''​) τότε αρκεί ​να γράψουμε το παρακάτω 
 + 
 +<code java> 
 +public static void printΝumbers(List<?​ extends Number> list) { 
 +    for (Number num: list) 
 +        System.out.print(num + " "); 
 +    System.out.println();​ 
 +
 +</​code>​ 
 + 
 +===== Σχέσεις κληρονομικότητας φραγμένων παραμετρικών τύπων δεδομένων ===== 
 + 
 +Όπως είδαμε οι τύποι ''​List<​Integer>''​ και ''​List<​String>''​ δεν διέπονται από καμία σχέση κληρονομικότητας. Ο κοινός πατέρας και τον δύο λιστών είναι ​η κλάση ''​List<?>''​, όπως φαίνεται παρακάτω 
 +{{ :​java:​generics_inheritance3.png?​500 |}} 
 + 
 +Γενικότερα, σχέσεις κληρονομικότητας μεταξύ φραγμένων τύπων ​ισχύουν με κριτήρια κατά ​πόσο μπορούμε να αντικαταστήσουμε ένα τύπο δεδομένων με έναν άλλο τύπο δεδομένων. Δείτε τα παρακάτω παραδείγματα κληρονομικότητας 
 +<code java> 
 +      List<?>​ 
 +         | 
 +         v 
 + ​List<?​ extends Number>​ 
 +         | 
 +         v 
 + ​List<?​ extends Integer>​ 
 +         | 
 +         v 
 +    List<​Integer>​ 
 +</​code>​ 
 + 
 +Αντίστοιχα ισχύουν 
 +<code java> 
 +      List<?>​ 
 +         | 
 +         v 
 + ​List<?​ super Integer>​ 
 +         | 
 +         v 
 + ​List<?​ super Number>​ 
 +         | 
 +         v 
 +    List<​Number>​ 
 +</​code>​ 
 + 
 +Ανάλογα ισχύουν και τα παρακάτω 
 +<code java> 
 +              List<? extends ​Number> ​                                  List<? super Integer>​ 
 +                        |                         ​και ​                          | 
 +       ​------------------------------------ ​                    ​------------------------------------ 
 +       ​| ​                                 |                     ​| ​                                 | 
 +       ​v ​                                 v                     ​v ​                                 v 
 +   ​List<​Number> ​                    ​List<​Integer> ​          ​List<​Number> ​                    ​List<​Integer>​ 
 +</​code>​ 
 + 
 +Δοκιμάστε να μεταγλωττίσετε τα παρακάτω παραδείγματα κώδικα για ​να επιβεβαιώσετε τα παραπάνω. 
 +<code java> 
 +List<? extends Νumber> numList = new ArrayList<>​();​ 
 +List<?> ​ objectList = numList; ​  
 +</​code>​ 
 +<code java> 
 +List<? extends Integer> intList = new ArrayList<>​();​ 
 +List<? extends Number> ​ numList = intList; ​  
 +</​code>​ 
 +<code java> 
 +List<​Integer>​ intList = new ArrayList<>​();​ 
 +List<? extends Integer> extendedIntList = intList; ​  
 +</​code>​ 
 + 
 +Ανάλογα 
 +<code java> 
 +List<? super Integer> intList = new ArrayList<>​();​ 
 +List<?>​ objectList = intList; ​  
 +</​code>​ 
 +<code java> 
 +List<? super Number> numList = new ArrayList<>​();​ 
 +List<? super Integer> inList = numList; ​  
 +</​code>​ 
 +<code java> 
 +List<​Number>​ numList = new ArrayList<>​();​ 
 +List<? super Number> extendedNumList = numList;  
 +</​code>​ 
 + 
 + 
 + 
 +Το παρακάτω σχήμα ​εξηγεί τις σχέσεις κληρονομικότητας που διέπουν (άνω και κάτω) φραγμένους τύπους δεδομένων για τον παραμετρικό τύπο δεδομένων της λίστας
 +{{ :java:generics_inheritance4.png?500 |}} 
 + 
 + 
 + 
java/generic_bounded_types.1426453736.txt.gz · Last modified: 2016/02/26 11:15 (external edit)