Declaraciones
Variable
1. ¿Qué es una variable?
a. Contenido
El contenido de una variable es su valor, almacenado en memoria. Se trata, obligatoriamente, de un objeto, dicho de otro modo, de la instancia de una clase. El tipo de la instancia es el nombre de su clase. Por ejemplo, 42 es una instancia de la clase int, es de tipo int:
>>> type(42)
<class 'int'>
Cualquier operación realizada sobre una variable se realiza sobre su valor.
b. Continente
El continente no es más que la asociación de un nombre, llamado identificador, y un puntero hacia el contenido, es decir, el valor asociado a dicho nombre.
La asignación es la operación que permite asociar un contenido (operando situado a la derecha) con un continente (operando situado a la izquierda) y, por tanto, asociar un identificador con un puntero a un valor.
>>> a = 42
De este modo, el uso de este nombre devuelve, sistemáticamente, el valor asociado:
>>> a
42
La única forma de eliminar esta asociación entre contenido y continente es suprimir la asociación entre el nombre y el puntero:
>>> del a
El continente ya no existe, y ya no es posible utilizar el nombre de la variable:
>>> a
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
NameError: name 'a' is not defined
El hecho de que el continente ya no exista no quiere decir, necesariamente, que el contenido asociado ya no exista en memoria, pues si bien un continente solo puede estar asociado a un único contenido, un contenido puede estar asociado a varios continentes.
Para saber si los continentes apuntan al mismo contenido, se realiza lo siguiente:
>>> a is b
He aquí un ejemplo en el que se elimina un continente pero no el contenido:
>>> a = 42
>>> b = a
>>> a is b
True
>>> del a
>>> b
42
Cuando todos los continentes que apuntaban sobre un contenido se eliminan, el contenido se vuelve inaccesible, en el sentido de que ya no tiene ningún puntero asociado.
Esto no significa que se vaya a eliminar inmediatamente, pues esta operación la realiza el recolector de basura de la máquina virtual de Python y este último se lanza de manera optimizada e impredecible....
Función
1. Declaración
La declaración de una función es muy sencilla, tal y como hemos visto en el capítulo anterior. Basta con utilizar la palabra clave def, seguida del nombre que se quiere dar a la función y paréntesis de apertura y cierre que pueden, si es preciso, contener una lista de argumentos, y los dos puntos.
Se abre, de este modo, un bloque que posee su propio espacio de nombres local y que contiene las instrucciones de la función. Termina devolviendo una variable y, si no se indica explícitamente mediante alguna instrucción, la función devuelve None.
El nombre de la función debe ser, preferentemente, un nombre representativo de esta. Este nombre es también el nombre de la variable (continente) cuyo valor es la función, que es un objeto (contenido).
Si ya existe una variable con el nombre de la función, se reemplaza por la función, exactamente de la misma manera que cuando se realiza una operación de asignación.
He aquí una función vacía:
>>> def f():
... pass
...
He aquí los atributos o métodos del objeto función:
>>> list(set(dir(f))-set(dir(object)))
['__module__', '__defaults__', '__annotations__',
'__kwdefaults__', '__globals__', '__call__', '__closure__',
'__dict__', '__name__', '__code__', '__get__']
Una función está vinculada con el nombre del módulo que contiene su definición:
>>> f.__module__
'__main__'
Vemos que lleva su mismo nombre:
>>> f.__name__
'f
Esta característica es propia de la función y no del nombre de la variable:
>>> g = f
>>> g.__name__
'f'
He aquí la misma función definida con un docstring:
>>> def f():
... """Docstring útil"""
...
La palabra clave pass ya no es necesaria, pues la función contiene una instrucción que es este docstring. Forma parte de la documentación del código, y resulta útil para aquellos que deban utilizarla, permitiendo realizar pruebas unitarias....
Clase
1. Declaración
a. Firma
Para declarar una clase, se utiliza la palabra clave class, seguida del nombre de la clase, de los padres entre paréntesis y de un bloque que representa la encapsulación de los datos de la clase, atributos y métodos.
He aquí la declaración mínima:
>>> class A:
... pass
...
Dicha sintaxis está prohibida en Python 2.x, donde hay que utilizar, obligatoriamente, las nuevas clases (nuevas desde la versión 2.2):
>>> class A(object):
... pass
...
El uso de esta última forma es, en Python3, exactamente idéntica a la forma anterior. El cambio de rama permite que la escritura con el estilo anterior cree la misma clase que con el nuevo estilo, dado que el antiguo ya no existe.
De este modo, independientemente de cómo se describa la clase anterior, se tiene:
>>> type. mro(A)
[<class '__main__.A'>, <class 'object'>]
b. Atributo
Uno de los principios esenciales de un lenguaje orientado a objetos es la encapsulación, que implica que un dato relativo a una clase pertenezca a la clase. La consecuencia es la necesidad de tener un mecanismo de acceso que permita encontrar el dato dentro de la clase o una instancia de la clase. Esto significa también, aparte de la programación orientada a objetos mediante prototipos, que estos datos se declaran en el bloque de la clase.
En Python, todo depende de la indentación:
>>> class A(object):
... atributo = 42 ...
Módulo
1. ¿Para qué sirve un módulo?
Un módulo es la agrupación de un conjunto de funcionalidades dentro de un mismo archivo. De este modo, su contenido depende exclusivamente de usted, incluso aunque existan buenas prácticas que conviene respetar.
Un módulo es, por tanto, un bloque en la construcción de su aplicación. Invocado directamente (ejecutado), se trata de un punto de entrada de su aplicación.
2. Declaración
Un módulo Python es, simplemente, un archivo con la extensión .py o .pyc (versión Python o versión compilada) o incluso un archivo escrito directamente en C (para la implementación CPython). También puede ser una carpeta.
Un módulo es, por tanto, un bloque que posee su espacio de nombres y que puede contener variables, funciones, clases, y también otros módulos.
A diferencia de otros lenguajes, no existen reglas en Python que impongan una clase por archivo o por módulo. Esto podría ser contraproducente, pues significaría que un módulo solo podría contener una única clase.
Es, también, contrario a las buenas prácticas de diseño de software que, en Python, aprovecha este concepto de módulo para permitir la implementación de una arquitectura de código flexible y lógico.
Un módulo Python puede integrar otro módulo y puede realizar una jerarquía más o menos compleja. Si los módulos de más bajo nivel son archivos, los módulos de alto nivel serán carpetas.
Estos módulos no contienen más que submódulos. No obstante, es posible agregar otro contenido creando, en la carpeta del módulo, un archivo __init__.py que contiene el código de los elementos específicos del módulo.
Cabe destacar que este archivo es obligatorio en Python 2.x, pues es lo que hace de cada carpeta un módulo Python. En Python 3.x, es útil únicamente para dar información suplementaria (declaraciones globales del módulo).
3. Instrucciones específicas
Hemos visto que para escribir una aplicación...