Catégories: PHP | Langage | Article
Visibilité des membres de classes en PHP
Un article de ToutProgrammer.com.
A l'arrivée de PHP 4, les développeurs ont pu très tôt se mettre à la programmation orientée objet. Mais tout membre de classe (attributs et méthodes) était totalement visible à l'extérieur de cet objet. A l'arrivée de PHP 5, un certain nombre des défauts de son aîné ont été corrigés. Voyons ce que cette version propose pour la visibilité des membres d'une classe.
Sommaire |
[modifier] La visibilité avec PHP 4
PHP 4 proposait une gestion des objets plus que basique. Voici ce que nous pouvions avoir pour une classe toute simple:
<?php class Utilisateur { var $nom; var $prenom; var $email; function Utilisateur($nom, $prenom) { $this->setNom($nom); $this->setPrenom($prenom); } function afficherInfo() { } function setNom($nom) { $this->nom = $nom; $this->determinerEmail(); } function setPrenom($prenom) { $this->prenom = $prenom; $this->determinerEmail(); } function determinerEmail() { // Méthode que le développeur ne doit pas appeler de lui même $this->email = $this->prenom.".".$this->nom."@sitebidon.fr"; } } $utilisateur =& new Utilisateur("MARTIN", "Jean"); $utilisateur->afficherInfo(); $utilisateur->prenom = "Paul"; $utilisateur->afficherInfo(); ?>
Comme nous le voyons, pour modifier directement un attribut, nous pouvons valoriser directement celui-ci. Mais en faisant cela, l'adresse email n'est pas mise à jour avec le nouveau prénom puisque la méthode determinerEmailn'est pas appelée implicitement. Nous pourrions utiliser le setter setPrenommais rien n'oblige à le faire.
La visibilité des membres des classes est une caractéristique importante de la programmation orientée objet. Elle permet d'indiquer les propriétés et les méthodes qui peuvent ou ne peuvent pas être utilisées à l'extérieur de la classe.
Comme nous le voyons dans le source, la méthode determinerEmailn'est pas destinée à être appelée de l'extérieur de la classe, mais rien ne l'interdit.
Voyons maintenant ce que PHP 5 fournit pour corriger cela.
[modifier] La visibilité accrue de PHP 5
PHP 5 comme beaucoup de langages orientés objet ajoute trois nouveaux mots clés: public, protected et private. Les personnes qui utilisent Java ou C++ ne seront pas dépaysées puisque ces mots réservés sont déjà très utilisés dans ces langages.
Voici un tableau décrivant brièvement leurs utilisations (du moins restrictif au plus restrictif):
| Mot clé | Fonctionnement |
|---|---|
| public | Sur une propriété ou une méthode, il autorise son utilisation depuis l'extérieur de l'objet. C'est le fonctionnement par défaut de PHP 4. |
| protected | Sur une propriété ou une méthode, il permet d'utiliser celle-ci uniquement à partir d'une classe descendante. |
| private | Sur un propriété ou une méthode, il permet d'interdire toute utilisation à l'extérieur de l'objet (même à partir d'une classe fille). Cela devrait être le cas de toute propriété puisque son accès devrait se faire uniquement avec des getters et des setters. |
Nous allons voir concrètement maintenant des exemples d'utilisation de ces mots clés.
[modifier] Exemple de visibilités avec PHP 5
Nous allons utiliser l'exemple vu pour PHP 4 mais adapté avec PHP 5 pour essayer de bien comprendre les besoins.
<?php class Utilisateur { private $nom; private $prenom; private $email; public function Utilisateur($nom, $prenom) { $this->setNom($nom); $this->setPrenom($prenom); } public function afficherInfo() { } public function setNom($nom) { $this->nom = $nom; $this->determinerEmail(); } public function getNom() { return($this->nom); } public function setPrenom($prenom) { $this->prenom = $prenom; $this->determinerEmail(); } public function getPrenom() { return($this->prenom); } public function getEmail() { return($this->email); } protected function setEmail($email) { $this->email = $email; } protected function determinerEmail() { $this->setEmail($this->getPrenom().".".$this->getNom()."@sitebidon.fr"); } } $utilisateur =& new Utilisateur("MARTIN", "Jean"); $utilisateur->afficherInfo(); $utilisateur->setPrenom("Paul"); $utilisateur->afficherInfo(); ?>
Ce qui affiche:
MARTIN Jean <Jean.MARTIN@sitebidon.fr> MARTIN Paul <Paul.MARTIN@sitebidon.fr>
Comme nous pouvons nous en rendre compte, nous avons remplacé les varpar des privatesur chacun des attributs comme cela avait été indiqué dans le tableau un peu plus haut. Ceci s'explique par le fait qu'un développeur doit éviter d'accéder directement à un attribut mais utiliser de préférence ce que l'on appelle un setter. Dans cette exemple, nous avons déclaré 2 setters publiques: setNom et setPrenom.
Nous avons également déclaré les méthodes afficherInfo, getNom, getPrenomet getEmailcomme publiques afin que le développeur puisse lire les valeurs des attributs mais en passant par ce que l'on appelle des getters.
Reste la méthode determinerEmailqui est chargée de créer l'adresse email. Le développeur n'a pas normalement à utiliser cette méthode, nous l'avons donc mise comme protégée. Nous en verrons les raisons quelques lignes plus bas.
Contrairement à l'exemple avec PHP 4, on peut voir que le fait de forcer l'utilisation d'un setter en interdisant l'accès aux attributs a permis d'avoir toujours une adresse email à jour même lorsque le prénom de l'utilisateur a été modifié.
Voyons maintenant pourquoi nous avons déclaré determinerEmailen tant que protected.
A cela 2 raisons:
- la méthode ne peut être appelée qu'à partir d'une classe enfant,
- nous allons pouvoir utiliser la surcharge qui est une caractéristique importante de la programmation orientée objet.
Nous allons imaginer que nous avons besoin de créer un accès à notre site pour des membres qui sont des utilisateurs avec en plus un identifiant et un mot de passe. Voici ce que nous pourrions ajouté à notre précédent exemple:
class Membre extends Utilisateur { private $identifiant; private $motdepasse; public function Membre($nom, $prenom, $identifiant, $motdepasse) { parent::Utilisateur($nom, $prenom); $this->setIdentifiant($identifiant); $this->setMotDePasse($motdepasse); } public function setIdentifiant($nom) { $this->identifiant = $identifiant; } public function getIdentifiant() { return($this->identifiant); } public function setMotDePasse($motdepasse) { $this->motdepasse = $motdepasse; } public function getMotDePasse() { return($this->motdepasse); } protected function determinerEmail() { $this->setEmail($this->getPrenom().".".$this->getNom()."@users.sitebidon.fr"); } }
Nous voyons que cette classe étend la classe Utilisateur. Nous avons surchargé la méthode de détermination de l'adresse email pour que les membres aient leur propre adresse avec @users.sitebidon.fr.
Si nous avions déclaré cette méthode publique, tout développeur aurait pu l'utiliser avec des risques éventuels.
Si nous l'avions déclarée privée, nous n'aurions pas pu la redéfinir.
Voici ce à quoi sert le mot clé protected.
[modifier] Historique de l'article
Cet article, réalisé par Stéphane VANPOPERYNGHE, a été publié pour la première fois le 4 juillet 2003 sur le site ToutProgrammer.com (1ème version).

