Guida della class PropertyObject

Sono nuovo di php e attualmente sto leggendo Wrox Professional PHP 5.

Qualcuno può spiegarmi il seguente codice?

<? php abstract class PropertyObject { //Stores name/value pairs that hook properties to database field names protected $propertyTable=arrays(); //List of properties that have been modified. protected $changedProperties=arrays(); //Actual data from the database. protected $data; //Any validation errors that might have occured. protected $errors=arrays(); public function __construct($arData) { $this->data=$arData; } function __get($propertyName) { if(!arrays_key_exits($propertyName,$this->propertyTable)) { throw new Exception("Invalid property \"$propertyName\" !"); } if(method_exists($this,'get'.$propertyName)) { return call_user_func(arrays($this,'get'.$propertyName)); } else { return $this->data[$this->propertyTable[$propertyName]]; } } function __set($propertyName,$value) { if(!arrays_key_exits($propertyName,$this->propertyTable)) { throw new Exception("Invalid property \"$propertyName\" !") } if(method_exits($this,'set'.$propertyName)) { return call_user_func(arrays($this,'set'.$propertyName),$value); } else { //If the value of the property really has changed and it's not already in the changedProperties arrays, add it. if($this->propertyTable[$propertyName] !=$value && !in_arrays($propertyName,$this->changedProperties)) { $this->changedProperties[]=$propertyName; } //Now set the new value $this->data[$this->propertyTable[$propertyName]]=$value; } } } ?> 

Non riesco a capire il codice all'interno del valutatore di get e impostare i methods.

Il metodo magico __get viene chiamato quando viene richiesta una properties; dell'object, ma non è stata dichiarata o specificatamente assegnata (per le properties; dinamiche). Questa implementazione:

  • Prima prova a vedere se la properties; logica esiste come una voce nella properties; dichiarata effettiva chiamata $propertyTable .
  • Se non esiste, genera un'exception, lasciando quindi il metodo,
  • Se esiste e addizionalmente esiste un metodo chiamato 'get'.$propertyName (cioè, "get" concatenato con il nome della properties; della richiesta), quel metodo viene chiamato e viene restituito il suo valore.
  • Se esiste ma non esiste un tale metodo, restituisce il valore della voce con la chiave $propertyName nella properties; dichiarata $propertyTable .

__set questo, penso che puoi capire __set . Vedi Magic Methods nel manuale PHP.

Questo è un modo molto comune di impostare una class di archiviazione DB. Quello che succede è istanziare un object basato su PropertyObject (come PropertyObject è astratto)

 class MyObj extends PropertyObject { } $m = new MyObj(); 

Che eredita i __get() e __set() . Ogni volta che si accede ai dati dell'object tramite l'operatore -> , vengono chiamati rispettivamente i methods __get() e __set() .

 $m->foo; #calls MyObject::__get('foo'); $m->bar = 'baz'; #calls MyObject::__set('bar','baz'); 

Il metodo __get() prima controlla se c'è una chiave definita nella tabella delle properties; (che qui modella i campi dal DB), e se uno non esiste, genera un'exception. Quindi, get() vedrà se c'è una function definita con la parola 'get' anteposta. Quindi, supponendo che foo fosse una chiave nella propertyTable __get() , __get() vedrebbe se abbiamo definito un metodo getfoo , e se lo avessimo, chiamatelo per noi e restituire il suo valore.

  //if(method_exists($this,'get'.$propertyName)) //{ // return call_user_func(arrays($this,'get'.$propertyName)); //} $m->foo; # checks if MyObj::getfoo is defined, and if so, calls it 

Infine, se nella propertyTable è presente un tasto foo ma nessun metodo denominato getfoo , restituisce semplicemente il valore della posizione dell'arrays in $m->data cui chiave è il valore della posizione dell'arrays in propertyTable cui chiave è foo

__set() è definito più o less allo stesso modo, ma piuttosto che restituire il valore archiviato nell'arrays di data controlla invece un 'set' preposto e controlla se il valore impostato sull'object è diverso dal valore nel arrays di data , e se lo è, aggiunge il nome della properties; alla matrix changedProperties prima di impostare il nuovo valore.