Estoy últimamente aprendiendo Python y lo que aprendo lo voy escribiendo en un curso de python en la chuwiki. Ya lo sabía desde hace tiempo y no me gustaba, pero en los ejemplos que he ido haciendo para el curso, me he tropezado con el problema de una forma inesperada.
¿Cual es el problema?. Básicamente que si tienes una clase Python, por ejemplo, esta
class Clase:
pass
Una simple clase, he puesto pass simplemente por no complicarme, pon ahí todo lo que quieras. Pues bien, si en código yo hago esto
Clase.pepe = ‘hola’
simplemente lo admite y crea el atributo pepe en la clase. Bien, esto puede ser estupendo, nos permite crear atributos de una forma dinámica si hace falta. Pero la pega que siempre he encontrado es que somos humanos y como humanos nos equivocamos, sobre todo al teclear. Estoy seguro que la tecla del del teclado es la más usada. ¿Qué pasa si la clase tiene un atributo nombre y nos equivocamos al teclearlo?
class Clase:
nombre = »Clase.nonbre = ‘Pedro’
Pues fácil, tenemos un atributo nombre sin valor y un nuevo atributo creado al vuelo nonbre con el valor correcto. No hace falta mucha imaginación para darse cuenta la de problemas de depuración que nos puede dar esto si no nos damos cuenta. De hecho, seguro que no habrías visto nada raro si no te digo la estadística de la tecla del antes.
Pero bueno, estoy ya lo sabía e incluso creo que lo comenté en algún post anterior. El problema con el que me he encontrado ahora es el siguiente. Imagina que tenemos la clase con el nombre y hacemos esto
>>> pedro = Clase()
>>> pedro.nombre = ‘Pedro’
>>> print(pedro.nombre)
‘Pedro’
>>> print(Clase.nombre)
»
Pues bien, resulta que hemos creado una instancia pedro, le hemos asignado un nombre y se lo ha asignado. Pero no en el atributo nombre de la clase, sino creando un atributo nombre específico para la instancia y que oculta el atributo nombre de la clase.
Todo correcto, es el comportamiento esperado de Python. Aunque no sé si me convence. Como he comentado, somos humanos. El atributo de clase es compartido por todas las instancias y podemos quizás querer cambiarle el valor en algún momento de la ejecución de nuestro código. La forma correcta de cambiarlo para que afecte a todas las instancias sería usando el nombre de la clase, es decir Clase.nombre=’valor para todas las instancias’. Pero los humanos seguimos siendo humanos y nos equivocamos, tanto programadores novatos como expertos. Los primeros se lo piensan mucho y meten la pata. Los segundo meten la pata directamente. Entra dentro de lo posible que al querer cambiar ese nombre de la clase usemos una instancia como en el ejemplo. Nuevamente un dolor de cabeza de depuración.
Sin quitarle valor a python, que se ha ganado su puesto como lenguaje más utilizado, sobre todo por temas de inteligencia artificial, este es el motivo por el que no me gustan los lenguajes en los que no se declaran las variables previamente para desarrollos en serio. Por desarrollo en serio me refiero a desarrollos grandes en los que hay implicados varios desarrolladores, humanos todos ellos. En un lenguaje con declaración de variables, si cualquier de ellos se equivoca al escribir el nombre de una variable, o la mete en una clase/instancia que no tiene que estar, como no se ha declarado previamente, el error salta según el programador humano hace sus cosas humanas. En lenguajes donde no es necesario declarar las variables, esto no «canta» hasta la ejecución, donde te tocará echar tiempo depurando.