Bienvenidos sean a este post, hoy hablaremos sobre dos conductas interesantes de las propiedades de una clase.
Shadowing
Esta conducta es una muy interesante del lenguaje porque cuando necesita una propiedad de un objeto y este no la encuentra sigue por toda la cadena de clases creadoras hasta llegar al final y notificar que no existe pero en caso de encontrar una en todo el proceso nos devuelve el valor de la misma, para entender este concepto vamos a utilizar el siguiente ejemplo:
>>> class Puntos:
... x = 10
... y = 7
...
>>> p = Puntos()
>>>
Creamos una clase llamada Puntos que contendra dos dimensiones (x e y) para luego crear un objeto de esta llamada p, nuestro siguiente paso sera crear una nueva propiedad de p que se llamara x:
>>> p.x = 12
Tal como vimos en el post anterior, este valor solo afectara a este objeto pero no cambiara el valor de la clase, veamos los valores:
>>> print(p.x)
12
>>> print(Puntos.x)
10
>>>
En este caso volvemos a ver lo mismo que en el post anterior donde todas las modificaciones en las clases u objetos siempre sera de arriba hacia abajo y no de abajo hacia arriba, pero que sucede si borramos el valor de x en el objeto p? primero borremos dicho valor con la siguiente funcion:
>>> del p.x
En este caso eliminamos que generamos en el objeto p, si volvemos a mostrar los valores sucedera lo siguiente:
>>> print(p.x)
10
>>>
Como pueden ver al no encontrar la propiedad x dentro del objeto procede a buscarla en su clase creadora, encuentra la propiedad y nos devuelve el valor que posee, pero recuerden que esto solo aplica a propiedades modificadas de la clase base de lo contrario devolvera un error, vamos a agregar una nueva propiedad al objeto que sera una nueva dimension:
>>> p.z = 15
Si lo mostramos el valor de z del objeto y de la clase nos sucedera lo siguiente:
>>> print(p.z)
15
>>> print(Puntos.z)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: type object 'Puntos' has no attribute 'z'
>>>
Sucede exactamente lo mismo a lo visto en el post anterior, este valor existe en el objeto pero no en la clase por lo tanto si nosotros lo eliminamos del objeto al intentar hacer un shadowing nos devolvera el mismo error porque nunca existio en la clase base, para redondear este concepto podemos decir que esta forma de trabajo siempre trabajara cuando la propiedad existe en la clase y esta modifico el valor en el objeto creada de esta, pasemos al siguiente tema.
self
Desde el metodo de una clase podemos referenciar a una instancia mediante un argumento especial llamado self, este sera siempre el primer atributo de un metodo de instancia, vamos a estudiar un ejemplo donde no solo podemos compartir propiedades sino tambien metodos, primero crearemos la clase:
>>> class Cuadrado:
... lado = 8
... def area(self):
... return self.lado ** 2
...
>>>
Para entender este concepto debemos entender el significado de self, en si mismo, es decir que siempre trabajara con los valores que contenga la instancia en si, por ejemplo aqui tenemos una propiedad llamada lado, despues definimos una funcion llamada area que como argumento recibe un self, lo cual simboliza una referencia a una instancia, despues le decimos que dicha instancia calcule el cuadrado del valor de lado que posea, pasemos a crear un objeto de esta clase:
>>> cd = Cuadrado()
Nuestro objeto ya esta creado probemos de ejecutar el valor de area:
>>> print(cd.area())
64
>>>
Como tiene solamente el valor de lado informado por la clase al ejecutarlo utilizara este para calcular el area del mismo, lo mismo sucede si al metodo area de la clase le pasamos la instancia cd:
>>> print(Cuadrado.area(cd))
64
>>>
Pero que sucedera si modificamos el valor de lado de nuestro objeto?, modifiquemos el mismo de la siguiente forma:
>>> cd.lado = 10
Con este dato modificado ejecutemos nuevamente el metodo area de esta instancia:
>>> print(cd.area())
100
>>>
Observen como en lugar de usar el valor de la clase uso el nuevo valor que creamos dentro de la instancia, esto nos permitira que cada objeto creado de esta clase pueda procesar los valores de sus propiedades y metodos independientemente unos de otros, veamos el siguiente ejemplo:
>>> ef = Cuadrado()
>>> print(ef.area())
64
>>> print(cd.area())
100
>>>
En este caso creamos un nuevo objeto llamado ef de la clase Cuadrado, si ejecutamos el area del mismo nos devolvera el valor en base al valor de lado que recibio, en cambio si volvemos a probar el area de nuestro objeto anterior veremos que este no se modifico en absoluto.
En resumen, hoy hemos visto que es shadowing, como trabaja este concepto, para que nos puede ser util y cual es su alcance, el siguiente tema visto fue self, como trabaja esta herramienta y como nos ayuda a la hora de independizar los objetos creados de la clase padre, espero les haya sido de utilidad sigueme en tumblr, Twitter o Facebook para recibir una notificacion cada vez que subo un nuevo post en este blog, nos vemos en el proximo post.


Donación
Es para mantenimento del sitio, gracias!
$1.00
