Foros del Web » Programando para Internet » PHP »

[SOLUCIONADO] Objetos anidados PHP

Estas en el tema de Objetos anidados PHP en el foro de PHP en Foros del Web. Buenas noches, estoy haciendo un pequeño juego y se me ha ocurrido hacerlo de una forma que me parece la mejor forma de hacerlo, el ...
  #1 (permalink)  
Antiguo 31/01/2015, 20:05
Avatar de Macf  
Fecha de Ingreso: agosto-2007
Mensajes: 29
Antigüedad: 17 años, 2 meses
Puntos: 0
Objetos anidados PHP

Buenas noches, estoy haciendo un pequeño juego y se me ha ocurrido hacerlo de una forma que me parece la mejor forma de hacerlo, el juego consiste en una ciudad, que tiene x edificios. Tengo un objeto que sea $ciudad con unas propiedades (como numero de habitantes, dinero, dueño, etc), que dentro tenga otro objeto por cada edificio, y que cada edificio tenga unas acciones que puede realizar, (por ejemplo: $ciudad->cuartel->entrenar(5,arqueros) ) todo funciona bien, creo las clases, instancio los objetos y todo va bien.

Código de ejemplo:
Código PHP:
<?php

class ciudad {
    public 
$edificio1;
    public 
$duenoId=1//Id del dueño de la ciudad
        
public $dinero=1000
}

class 
Edificio1 {
    
    public function 
subirNivel() {
        echo 
'estoy subiendo un nivel del edificio1</br>';
    }
}

    
$ciudad1= new Ciudad;
    
$ciudad1->edificio1= new Edificio1;
    
$ciudad1->edificio1->subirNivel();
    echo 
$objeto1->duenoId;
?>
Mi pregunta es, ¿hay alguna forma, para que pueda acceder a las propiedades del objeto ciudad1 desde dentro del objeto edificio1? Por ejemplo, si cuando yo dijera subir 1 nivel del edificio1, tuviera que saber la id del dueño de la ciudad (propiedad duenoId) para hacer la consulta a la base de datos, o restarle el dinero que cueste construir el edificio al subir el nivel ¿como lo podría hacer?

Quizás la forma que tengo de enfocarlo no sea la mejor, o directamente sea imposible, pero solo por poder hacer $ciudad->cuartel->entrenar(5,arqueros) tengo que intentarlo.

Un saludo, y gracias de antemano.
  #2 (permalink)  
Antiguo 31/01/2015, 21:24
Avatar de pateketrueke
Modernizr
 
Fecha de Ingreso: abril-2008
Ubicación: Mexihco-Tenochtitlan
Mensajes: 26.399
Antigüedad: 16 años, 7 meses
Puntos: 2534
Respuesta: Objetos anidados PHP

No hay una manera directa de saberlo, sin embargo podrías pasar por referencia el "padre" cada que instancías un nuevo hijo.

Así el hijo puede saber en todo momento quien es su padre:
Código PHP:
Ver original
  1. class Parent {}
  2. class Child {
  3.   public function __constructor($parent) {
  4.     $this->parent = $parent;
  5.   }
  6. }
  7.  
  8. $p = new Parent();
  9. $c = new Child($p)
  10. $c->parent === $p; // TRUE
__________________
Y U NO RTFM? щ(ºдºщ)

No atiendo por MP nada que no sea personal.
  #3 (permalink)  
Antiguo 01/02/2015, 11:43
Avatar de Macf  
Fecha de Ingreso: agosto-2007
Mensajes: 29
Antigüedad: 17 años, 2 meses
Puntos: 0
Respuesta: Objetos anidados PHP

Lamentablemente no puedo hacerlo con tu método porque si tengo muchos edificios, y muchas ciudades, tendría que duplicar decenas de veces el mismo objeto, y aun así no podría cambiar ninguna propiedad del objeto padre desde alguna función de los objetos hijos. No obstante leyendo tu solución se me ocurrió una que si que he conseguido que funcione, quizás no sea demasiado bonita y un pelín enrevesada, pero consigo todo lo que necesito hacer.

Le paso el nombre del objeto padre al objeto hijo cuando lo creo, y después si dentro del objeto hijo declaro la variable del objeto padre como global puedo acceder a ella desde "fuera" pero desde el objeto hijo, es decir, puedo acceder a las propiedades y métodos públicos del padre desde dentro del hijo.

Aquí está el código nuevo funcionando, como se puede ver soy capaz de acceder a las propiedades del objeto ciudad1 (nombre y habitantes) desde el objeto hijo edificio1, y cambiarlas (cambio el número de habitantes de la ciudad1 con $ciudad1->edificio1->cambiarHabitantes(17000) )
Código PHP:
<?php

    error_reporting
(E_ALL);
    
ini_set('display_errors''1');
    
class 
Ciudad {
    public 
$nombre//Nombre de la ciudad (Madrid, Barcelona, ...)
    
public $habitantes=15000//Codigo postal ciudad
    
    
public $edificio1//Edificio1 de la ciudad
    
    
    
public function __construct($nombreCity,$nombreVar){
        
$this->nombre=$nombreCity//Guardo nombre ciudad
        
$this->edificio1= new Edificio1($nombreVar); //Instancio obj hijo Edificio1 pasando nombre obj padre
    
}
    
    public function 
showhabitantes(){
        echo 
'Número de habitantes: '.$this->habitantes;
    }
}

class 
Edificio1 {
    public 
$parent;
    
    
    public function 
__construct($parent){
        
$this->parent=$parent;
    }
    
    public function 
ciudad(){
        global ${
$this->parent};
        echo 
'Pertenezco a la ciudad: '.${$this->parent}->nombre;
    }
    
    public function 
cambiarHabitantes($newHabitantes){
        global ${
$this->parent};
        ${
$this->parent}->habitantes=$newHabitantes;
    }
}

    
$ciudad1= new Ciudad('Madrid','ciudad1');
    
$ciudad1->edificio1->ciudad();
    echo 
'</br>';
    
$ciudad1->showHabitantes();
    
$ciudad1->edificio1->cambiarHabitantes(17000);
    echo 
'</br>';
    
$ciudad1->showHabitantes();
    
?>
Muchisimas gracias por tu ayuda, sin ti no habria dado con la solución.
  #4 (permalink)  
Antiguo 01/02/2015, 13:04
Avatar de pateketrueke
Modernizr
 
Fecha de Ingreso: abril-2008
Ubicación: Mexihco-Tenochtitlan
Mensajes: 26.399
Antigüedad: 16 años, 7 meses
Puntos: 2534
Respuesta: Objetos anidados PHP

Pues definitivamente te gusta hacer las cosas mal, no tenías la necesidad de rebuscar una solución que además es frágil.

Mira, acabo de corregir tu código usando el mismo concepto que te expliqué anteriormente:
Código PHP:
Ver original
  1. <?php
  2.  
  3.     error_reporting(E_ALL);
  4.     ini_set('display_errors', '1');
  5.  
  6. class Ciudad {
  7.     public $nombre; //Nombre de la ciudad (Madrid, Barcelona, ...)
  8.     public $habitantes=15000; //Codigo postal ciudad
  9.  
  10.     public $edificio1; //Edificio1 de la ciudad
  11.  
  12.  
  13.     public function __construct($nombreCity){
  14.         $this->nombre=$nombreCity; //Guardo nombre ciudad
  15.         $this->edificio1= new Edificio1($this); //Instancio obj hijo Edificio1 pasando nombre obj padre
  16.        // ¿por qué pasar el nombre y no la instancia en su lugar? ¿no te parece absolutamente fuera de sentido?
  17.     }
  18.  
  19.     public function showhabitantes(){
  20.         echo 'Número de habitantes: '.$this->habitantes;
  21.     }
  22. }
  23.  
  24. class Edificio1 {
  25.     public $parent;
  26.  
  27.  
  28.     public function __construct($parent){
  29.         $this->parent=$parent;
  30.     }
  31.  
  32.     public function ciudad(){
  33.         echo 'Pertenezco a la ciudad: '.$this->parent->nombre;
  34.     }
  35.  
  36.     public function cambiarHabitantes($newHabitantes){
  37.         $this->parent->habitantes=$newHabitantes;
  38.     }
  39. }
  40.  
  41.     $ciudad1= new Ciudad('Madrid');
  42.     $ciudad1->edificio1->ciudad();
  43.     echo '</br>';
  44.     $ciudad1->showHabitantes();
  45.     $ciudad1->edificio1->cambiarHabitantes(17000);
  46.     echo '</br>';
  47.     $ciudad1->showHabitantes();
  48.  
  49. ?>

Funciona exactamente igual que lo que hiciste tu pero sin la fragilidad de las variables globales ¿cómo se te ocurrió tan mala solución?

Además incluso ahorré bytes de código, no había razón para usar globales ni nada de estilo, con el sólo paso de referencias era suficiente.

Al final en tu solución terminabas pasando el "nombre de la variable global" con el objetivo de poder acceder a ella posteriormente, dentro de la instancia "edificio1" sin embargo es absolutamente innecesario.

¿Que no es más fácil pasar la referencia del objeto que solo el nombre si al final terminas accediendo a la instancia?

Por favor consulta una referencia de OOP.
__________________
Y U NO RTFM? щ(ºдºщ)

No atiendo por MP nada que no sea personal.
  #5 (permalink)  
Antiguo 01/02/2015, 15:36
Avatar de Macf  
Fecha de Ingreso: agosto-2007
Mensajes: 29
Antigüedad: 17 años, 2 meses
Puntos: 0
Respuesta: Objetos anidados PHP

Mil disculpas por haber puesto en duda tu solución, tenia un pequeño pero grave error de concepto, creia que lo que estaba haciendo al hacer
Código PHP:
public function __construct($parent){
            
$this->parent=$parent;
        } 
Era algo así como "duplicar" el objeto ciudad1 dentro del propio objeto edificio1, con lo que aunque si podía acceder a las propiedades del padre en realidad estaba accediendo al duplicado, por lo que si editaba una propiedad del "duplicado" no se cambiaría en efecto en el objeto real $ciudad1, pero todo lo contrario. Muchísimas gracias por tu ayuda, si llego a empezar a hacer algo con mi "solución" y luego me doy cuenta de que se hacia con la tuya habría tenido que por lo menos tirarme de un puente o algo parecido.

Un saludo.

Etiquetas: anidados, objetos
Atención: Estás leyendo un tema que no tiene actividad desde hace más de 6 MESES, te recomendamos abrir un Nuevo tema en lugar de responder al actual.
Respuesta




La zona horaria es GMT -6. Ahora son las 20:18.