Witaj Gościu! ( Zaloguj | Rejestruj )

Forum PHP.pl

 
Reply to this topicStart new topic
> Nadpisywanie składnika i sterowanie dostępem w klasie dziedziczącej
amii
post 28.05.2011, 11:04:20
Post #1





Grupa: Zarejestrowani
Postów: 728
Pomógł: 76
Dołączył: 12.06.2009

Ostrzeżenie: (0%)
-----


Przykład skopiowany z manula, więc myślę że źródło najbardziej wiarygodne jakie może być:
http://www.php.net/manual/pl/language.oop5.visibility.php
Jednej rzeczy nie rozumiem dlaczego w klasie MyClass2 nie można się odwołać do echo $obj2->protected; skoro wcześniej zasłania ona zmienną z klasy podstawowej zresztą jeśli jest protected to nawet gdyby nie było zasłonięcia powinniśmy się móc odwołać do składnika protected z klasy podstawowej

  1. <?php
  2. /**
  3.  * Define MyClass
  4.  */
  5. class MyClass
  6. {
  7. public $public = 'Public';
  8. protected $protected = 'Protected';
  9. private $private = 'Private';
  10.  
  11. function printHello()
  12. {
  13. echo $this->public;
  14. echo $this->protected;
  15. echo $this->private;
  16. }
  17. }
  18.  
  19. $obj = new MyClass();
  20. echo $obj->public; // Works
  21. echo $obj->protected; // Fatal Error OK odwołanie z zewnątrz do składnika chronionego
  22. echo $obj->private; // Fatal Error OK odwołanie z zewnątrz do składnika prywatnego
  23. $obj->printHello(); // Shows Public, Protected and Private OK wywołanie funkcji publicznej z zewnątrz (funkcja może grzebać w prywatnych składnikach swojej klasy)
  24.  
  25.  
  26. /**
  27.  * Define MyClass2
  28.  */
  29. class MyClass2 extends MyClass
  30. {
  31. // We can redeclare the public and protected method, but not private
  32. protected $protected = 'Protected2'; //zasłania zmienną z klasy podstawowej questionmark.gif?
  33.  
  34. function printHello()
  35. {
  36. echo $this->public;
  37. echo $this->protected;
  38. echo $this->private;
  39. }
  40. }
  41.  
  42. $obj2 = new MyClass2();
  43. echo $obj2->public; // Works
  44. echo $obj2->private; // Undefined OK bo składnik prywatny
  45. echo $obj2->protected; // Fatal Error questionmark.gif? dlaczego nie wywołuje składnika ze swojej klasy, który powinien zasłonić składnik z klasy podstawowej
  46. $obj2->printHello(); // Shows Public, Protected2, Undefined //OK wywołanie funkcji, która zasłania tą z klasy podstawowej mimo, że jest to funkcja z klasy MyClass2 wyświetla odziedziczony składnik public z klasy MyClass i zasłaniający składnik protected z klasy MyClass2 składnik private jest niedostępny.
  47.  
  48. ?>


Ten post edytował amii 28.05.2011, 11:15:32


--------------------
gry flash online
Dobry hosting i tanie odnowienia domen firma: masternet.
Zarabianie bez wysiłku na domenach bez ruchu: prolink.
Go to the top of the page
+Quote Post
Zyx
post 28.05.2011, 11:20:13
Post #2





Grupa: Zarejestrowani
Postów: 952
Pomógł: 154
Dołączył: 20.01.2007
Skąd: /dev/oracle

Ostrzeżenie: (0%)
-----


Dlatego, że odwołujesz się do niego w kodzie, który nie znajduje się ani w klasie MyClass, ani MyClass2.


--------------------
Specjalista ds. głupich i beznadziejnych, Zyx
Nowości wydawnicze: Open Power Collector 3.0.1.0 | Open Power Autoloader 3.0.3.0
Go to the top of the page
+Quote Post
amii
post 28.05.2011, 11:27:40
Post #3





Grupa: Zarejestrowani
Postów: 728
Pomógł: 76
Dołączył: 12.06.2009

Ostrzeżenie: (0%)
-----


I wszystko jasne smile.gif dopiero zaczynam się uczyć obiektówki i takie rzeczy męczą a dla starych wyjadaczy to zapewne pestka.

Poprawna wersja:
  1. class MyClass2 extends MyClass
  2.  
  3. {
  4.  
  5. // We can redeclare the public and protected method, but not private
  6.  
  7. protected $protected = 'Protected2'; //zasłania zmienną z klasy podstawowej
  8.  
  9.  
  10. function printHello()
  11.  
  12. {
  13.  
  14. echo $this->public;
  15. echo $this->protected;
  16. echo $this->private;
  17.  
  18. }
  19.  
  20.  
  21. echo $this->protected; //tu już można i wyświetli Protected2
  22. echo self::protected; //tak samo jak wyżej ?
  23. echo MyClass::protected; //można też tak operatorem zakresu sięgnąć do zasłoniętego składnika z klasy podstawowej i wyświetli Protected
  24. echo parent::protected; //tak samo jak wyżej ?
  25.  
  26. }




Ten post edytował amii 28.05.2011, 11:33:41


--------------------
gry flash online
Dobry hosting i tanie odnowienia domen firma: masternet.
Zarabianie bez wysiłku na domenach bez ruchu: prolink.
Go to the top of the page
+Quote Post
Crozin
post 28.05.2011, 12:54:37
Post #4





Grupa: Zarejestrowani
Postów: 6 476
Pomógł: 1306
Dołączył: 6.08.2006
Skąd: Kraków

Ostrzeżenie: (0%)
-----


Jak rozumiem ten kod, który opatrzyłeś komentarzami jest umieszczony wewnątrz jakiejś metody, tak?

Operator paamayim nekudotayim (genialna nazwa swoją drogą) używany jest przy odwołaniach statycznych. Wyjątkiem jest jedynie tutaj konstrukcja "parent::xxx" (deweloperzy PHP popisali się tutaj inteligencją...). Właściwości dynamicznych nie możesz używać jak statycznych (self::, MyCLass::$protected) - musiałbyś zadeklarować je jako statyczne (wtedy zaś nie mógłbyś się do nich odwoływać jak do dynamicznych).
Go to the top of the page
+Quote Post
amii
post 28.05.2011, 14:18:57
Post #5





Grupa: Zarejestrowani
Postów: 728
Pomógł: 76
Dołączył: 12.06.2009

Ostrzeżenie: (0%)
-----


Teraz te odwołania są w metodzie printHello()
1. Czyli jak rozumiem mamy tu dwa rodzaje dostępu dla składników statycznych (które mogą być zasłonięte lub nie) i do składników dynamicznych (które mogą być zasłonięte lub nie) tak jak we wzorcu poniżej.


  1. class MyClass2 extends MyClass
  2.  
  3. {
  4.  
  5. // We can redeclare the public and protected method, but not private
  6.  
  7. protected $protected = 'Protected2'; //zasłania zmienną z klasy podstawowej
  8.  
  9.  
  10. function printHello()
  11.  
  12. {
  13.  
  14. echo 'Zmienna chroniona klasy ' .__CLASS__. ' ma wartość: '.$this->protected . '<br>'; //tu już można i wyświetli Protected2
  15. //echo self::protected; niepoprawne bo używany do odwołań statycznych poprawny byłby gdyby zmienna protected była static
  16. //echo MyClass::protected; niepoprawne bo używany do odwołań statycznych poprawny byłby gdyby zmienna protected była static
  17. echo 'Zmienna chroniona zasłonięta dla klasy podstawowej dla ' .get_class($this). ' ma wartość: '. parent::protected . '<br>'; //czyli tak sięgamy do zasłoniętych składników z klasy podstawowej nie mających przydomka static ?
  18.  
  19. }
  20.  
  21.  
  22. }
  23.  
  24. //jesteśmy o obszarze globalnym poza klasą
  25. $MyClass = new MyClass1(); //tworzymy instancję obiektu klasy podstawowej
  26. $MyClass2 = new MyClass2(); //tworzymy instancję obiektu klasy pochodnej
  27.  
  28. //$MyClass->printHello(); //to jest jasne
  29. $MyClass2->printHello();
  30. /* OUTPUT
  31. Zmienna chroniona klasy MyClass2 ma wartość: Protected2
  32. Zmienna chroniona zasłonięta dla klasy podstawowej dla MyClass2 ma wartość: Protected
  33. */


--------------------
gry flash online
Dobry hosting i tanie odnowienia domen firma: masternet.
Zarabianie bez wysiłku na domenach bez ruchu: prolink.
Go to the top of the page
+Quote Post

Reply to this topicStart new topic
1 Użytkowników czyta ten temat (1 Gości i 0 Anonimowych użytkowników)
0 Zarejestrowanych:

 



RSS Wersja Lo-Fi Aktualny czas: 26.04.2024 - 05:25