115 votes

Comment écrire dynamiquement le nom d'une propriété d'un objet PHP ?

J'ai des propriétés d'objet dans mon code qui ressemblent à ceci :

$obj ->field_name_cars[0];
$obj ->field_name_clothes[0];

Le problème est que j'ai des centaines de noms de champs et que je dois écrire le nom de la propriété de façon dynamique. Sinon, le nom de l'objet et les clés de la propriété seront toujours les mêmes. J'ai donc essayé :

$obj -> $field[0];

En espérant que le nom de la propriété soit modifié dynamiquement et accède aux valeurs correctes. Mais je continue à obtenir 'undefined property $field in stdClass::$field ;

J'essaie plus ou moins d'écrire dynamiquement le php avant qu'il ne s'exécute afin qu'il puisse sortir les valeurs appropriées. Des idées sur la façon d'aborder cela ?

275voto

Jon Points 194296

Mise à jour pour PHP 7.0

Introduction de PHP 7 des changements dans la façon dont les variables et les propriétés indirectes sont traitées au niveau de l'analyseur syntaxique (voir le RFC correspondant pour plus de détails). Cela rapproche le comportement réel de celui attendu, et signifie que dans ce cas-ci $obj->$field[0] produira le résultat attendu.

Dans les cas où le comportement par défaut (désormais amélioré) n'est pas souhaité, les accolades peuvent toujours être utilisées pour le remplacer, comme indiqué ci-dessous.

Réponse originale

Écrivez l'accès comme ceci :

$obj->{$field}[0]

Cette astuce "entourer d'accolades" est utile en PHP chaque fois qu'il y a une ambiguïté due à des variables.

Considérons le code initial $obj->$field[0] -- cela signifie-t-il "accéder à la propriété dont le nom est donné en $field[0] "ou "accéder à l'élément avec la clé 0 de la propriété dont le nom est donné dans $field " ? Les accolades vous permettent d'être explicite.

41voto

Mike Brant Points 39322

Je pense que vous recherchez une notation de type variable-variable qui, lorsqu'on accède aux valeurs d'autres tableaux/objets, est mieux réalisée en utilisant une syntaxe de crochets comme celle-ci :

$obj->{field[0]}

11voto

JvdBerg Points 11579

La méthode magique __get est votre amie :

class MyClass
{
   private $field = array();

   public function __get($name)
   {
      if(isset($this->field[$name]))
        return $this->field[$name];
      else
        throw new Exception("$name dow not exists");
   }
}

Utilisation :

$myobj = new MyClass();
echo $myobj->myprop;

Explication : Toutes les données de vos champs sont stockées dans un tableau. Lorsque vous accédez à $myobj->myprop cette propriété n'existe évidemment pas dans la classe. C'est là que __get s'appelle. __get recherche le nom dans le field et renvoie la valeur correcte.

4voto

Jordan Georgiadis Points 301

Aujourd'hui, je relève ce défi. J'ai fini par adopter ce style de développement

$countTickets = new \stdClass;

foreach ($tickets as $key => $value) {

    if(!isset($countTickets->total)){
        $countTickets->total = 0;
    }

    if(!isset($countTickets->{$value['categoryname']})){
        $countTickets->{$value['categoryname']} = 0;
    }

    $countTickets->total += $value['number'];
    $countTickets->{$value['categoryname']} += $value['number']; 
}

-1voto

Peter Schaeffer Points 98

J'ai travaillé sur un code qui utilisait des propriétés d'objets créés dynamiquement. Je pensais que l'utilisation de propriétés d'objets créées dynamiquement était plutôt cool (vrai, à mon avis). Cependant, mon programme prenait 7 secondes pour s'exécuter. J'ai supprimé les propriétés d'objet dynamiques et les ai remplacées par des propriétés d'objet déclarées comme faisant partie de chaque classe (publique dans ce cas). Le temps CPU est passé de plus de 7 secondes à 0,177 secondes. C'est assez substantiel.

Il est possible que je fasse quelque chose de mal dans la façon dont j'utilise les propriétés dynamiques des objets. Il est également possible que ma configuration soit défectueuse d'une manière ou d'une autre. Bien sûr, je dois préciser que j'ai une configuration PHP très simple sur ma machine.

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