3 votes

PHP OOP : Méthode unique par type d'argument ?

Je suis en train d'écrire un petit ORM maison (intérêt académique). J'essaie d'adhérer au concept TDD en tant qu'exercice d'entraînement, et dans le cadre de cet exercice, j'écris de la documentation pour l'API au fur et à mesure que je développe la classe.

Exemple concret : je travaille sur une classe de mappeur classique de type "getCollection". Je veux qu'elle soit capable de récupérer des collections d'actifs X (disons des articles de blog) pour un utilisateur spécifique, ainsi que des collections basées sur un tableau arbitraire de valeurs numériques. Ainsi, vous pourriez avoir une méthode comme l'une des suivantes

$User = $UserMapper->load(1);
$ArticleCollection = $ArticleMapper->getCollection(range(10,20));
$ArticleCollection = $ArticleMapper->getCollection($User);
$ArticleCollection = $ArticleMapper->getCollection($User->getId());

Ainsi, lors de la rédaction de la documentation relative à la méthode getCollection, je souhaite déclarer la variable @param dans le bloc de documentation. Est-il préférable d'avoir une méthode unique pour chaque type d'argument, ou est-il acceptable d'avoir une méthode qui délègue à la bonne méthode/classe interne en fonction du type d'argument ?

6voto

Gordon Points 156415

Il est acceptable d'avoir une méthode qui délègue à la bonne méthode interne. Vous pourriez le documenter comme ceci :

@param Array|User|Integer $argName optional explanation

mais là encore, rien ne vous empêche d'avoir une méthode chacun

public function getCollectionByRange(array $range)
public function getCollectionByUser(User $user)
public function getCollectionByUserId($id)

En outre, vous pouvez utiliser le magie __call méthode pour prétendre que les méthodes ci-dessus existent, puis capturer les appels à ces méthodes et les déléguer à vos méthodes internes ( ZF le fait pour trouver les lignes dépendantes de la base de données. ). Vous devez documenter ces méthodes avec la balise @method dans le DocBlock de la classe. Mais gardez à l'esprit que les méthodes magiques sont toujours plus lentes que le fait d'avoir et/ou d'appeler directement les méthodes appropriées.

Utilisez ce qui vous semble le plus logique pour votre application et votre cas d'utilisation.

1voto

artlung Points 13433

Il sons Par exemple, vous voulez surcharger des fonctions, mais PHP (même PHP5) ne permet pas de surcharger des fonctions comme en Java, par exemple. Le site Section surcharge dans le manuel PHP n'est pas surcharge des fonctions :

Note : L'interprétation de PHP de "surcharge" est différente de celle de la plupart langages orientés objet. La surcharge fournit traditionnellement la possibilité de d'avoir plusieurs méthodes avec le même nom mais avec des quantités et des types d'arguments.

Vous pourriez vouloir dire ceci :

class ArticleMapper {
   public function getCollection($param) {
      if (is_array($param)) { $this->getCollectionByArray($param); }
      if (is_int($param)) { $this->getCollectionByInt($param); }
      if (is_a($param, 'User')) { $this->getCollectionByUser($param); }
   }
   private function getCollectionByArray(array $param) { ... }
   private function getCollectionByInt($param) { ... }
   private function getCollectionByUser(User $param) { ... }
}

Cela me semble être une bonne façon de le faire.

1voto

Stefan Gehrig Points 47227

Vous pourriez obtenir quelque chose comme surcharge des méthodes en vérifiant le type du paramètre passé au moment de l'exécution (PHP ne supporte pas ce concept connu d'autres langages comme ADA, Java, C# ou C++ par exemple) :

[...]
/**
 * @param  User|array|integer $user
 * @return array
 */
public function getCollection($user) {
    // perhaps a switch-case would be better here
    if ($user instanceof User) {
        // do what has to be done if you passed in a User object
    } else if (is_int($user) {
        // do what has to be done if you passed in a user id
    } else if (is_array($user)) {
        // do what has to be done if you passed in an array of user ids
    }
}
[...]

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X