Tipos de datos en Python

Tipos de datos en Python

Los tipos en Python son una representación de los datos, ya que no requiere que las variables declaren su tipo, porque todos los tipos se convierten de forma automática

Podemos utilizar la función type para conocer el tipo de una variable

Tipo booleano

El tipo booleano simplemente distingue entre dos estados, un estado de éxito o de activado, valor verdadero, True, y un estado de fracaso o de desactivado, valor falso, False

Ambos estados no son susceptibles a mayúsculas y minúsculas

Normalmente, el resultado de operadores que devuelven un valor de tipo booleano son pasados a las estructura de control

Tipos numéricos

En Python existen 4 tipos diferentes de variables numéricas:

  • int

    número entero con precisión fija

  • long

    número entero en caso de sobrepasar el tamaño de un int

  • float

    número en coma flotante de doble precisión

  • complex

    número complejo (parte real + j parte imaginaria)

Es el intérprete el que decide el tipo de variable según lo que definimos

Sin embargo, podemos querer forzarlo nosotros mediante un cast

Tipo string

Un string es una cadena de caracteres delimitadas por comillas

Un literal de tipo string se puede especificar de dos formas diferentes:

  • entrecomillado simple

    se especifican entre los carácteres de apertura y de cierre

    Para especificar una comilla simple literal, se ha de escapar con una barra invertida (\). Para especificar una barra invertida literal, se duplica (\\)

    Todas las demás instancias de barras invertidas serán tratadas como una barra invertida literal: esto significa que otras secuencias de escape que podrían utilizarse, tales como \r o \n, serán mostradas literalmente tal y como se especifican, en lugar de tener cualquier otro significado especial

  • entrecomillado doble

    se especifican entre los carácteres " de apertura y " de cierre

    Python interpretará las siguientes secuencias de escape como caracteres especiales:

    Código Descripción
    \n avance de línea (LF o 0x0A (10) en ASCII)
    \r retorno de carro (CR o 0x0D (13) en ASCII)
    \t tabulador horizontal (HT o 0x09 (9) en ASCII)
    \\ barra invertida
    \" comillas dobles

Métodos

Vamos a ver algunos de los métodos para cadenas de uso más cotidiano

Métodos de formato

Afectan al formato del texto contenido en la cadena

  • capitalize()

    Realiza una copia de la cadena con la primera letra en mayúsculas

  • lower()

    Devuelve una copia de la cadena en minúsculas

  • upper()

    Devuelve una copia de la cadena en mayúsculas

  • swapcase()

    Devuelve una copia de la cadena en la que las mayúsculas son minúsculas y viceversa

  • title()

    Devuelve una copia de la cadena en la que la primera letra de cada palabra es mayúscula y las demás minúsculas

  • center(longitud, ‘caracter de relleno’)

    Devuelve una copia de la cadena de entrada centrada en la longitud indicada y entre el caracter de relleno que se indique

  • ljust(longitud, ‘caracter de relleno’): Devuelve una copia de la cadena alineada a la izquierda

  • rjust(longitud, ‘caracter de relleno’)

    Devuelve una copia de la cadena alineada a la izda/derecha

  • zfill(longitud)

    Devuelve una copia de la cadena rellenada con ceros a la izda hasta alcanzar la longitud indicada

Métodos de búsqueda

Nos permiten buscar dentro de una determinada cadena para comprobar si una subcadena está contenida en la cadena o cuántas veces aparece una subcadena

  • count(‘subcadena’)

    Devuelve un entero representando la cantidad de apariciones de la subcadena dentro de la cadena

  • find(‘subcadena’)

    Devuelve un entero representando la posición en la que empieza la subcadena dentro de la cadena

Métodos de validación

Nos devuelven siempre un booleano, es decir, True o False

Sirven para comprobar si una cadena cumple una determinada condición

  • startswith(‘subcadena’)

    Nos dice si una cadena comienza por una cadena determinada

  • endswith(‘subcadena’)

    Nos dice si una cadena termina por una cadena determinada

  • isalnum()

    Nos dice si una subcadena es alfanumérica

  • isalpha()

    Nos dice si una cadena es alfabética

  • isdigit()

    Nos dice si una cadena es numértica

  • islower()

    Nos dice si una cadena contiene sólo minúsculas

  • isupper()

    Nos dice si una cadena contiene sólo mayúsculas

  • isspace()

    Nos dice si una cadena contiene sólo espacios en blanco

  • istitle()

    Nos dice si una cadena tiene formato de título

Métodos de sustitución

Nos permiten sustituir texto para unificar el formato de diferentes cadenas que nos han llegado por vías diferentes

  • format(argumentos)

    Podemos tener una cadena que esté preparada para recibir una cierta cantidad de argumentos

    Al llamar a esta función e introducir los argumentos necesarios nos devuelve una copia de la cadena ya formateada

  • replace(‘subcadena buscada’, ‘subcadena que poner’)

    Busca dentro de la cadena una subcadena y la sustituye por la cadena indicada

  • strip()

    Elimina el carácter que indiquemos de la derecha y de la izquierda de la cadena

    Por defecto busca el carácter espacio

  • lstrip()

    Elimina los caracteres a la izquierda de una cadena

    Si introducimos como argumento una subcadena, busca esa subcadena y las combinaciones de los caracteres de la subcadena desde la izquierda hasta que no encuentre ninguno más

  • rstrip()

    Elimina los caracteres a la a derecha de una cadena

    Si introducimos como argumento una subcadena, busca esa subcadena y las combinaciones de los caracteres de la subcadena desde la derecha hasta que no encuentre ninguno más

Métodos de unión y división

Nos permiten sustituir texto para unificar diferentes cadenas que nos han llegado por vías diferentes o para separar una cadena en varias

  • join(iterable)

    Recibe como argumento un iterable y devuelve como resultado los elementos del iterable unidos por el carácter de la cadena sobre la que se aplica

  • partition(‘separador’)

    Devuelve una tupla de 3 elementos

    El primer elemento es lo que hay a la izquierda del ‘separador’, el segundo elemento es el separador y el tercer elemento es lo que hay a la derecha del separador

  • split(‘separador’)

    Devuelve una lista con todos los elementos encontrados al dividir la cadena por el separador

  • splitlines()

    Devuelve una lista donde cada elemento es una fracción de la cadena dividida en líneas

Listas

Se definen poniendo el contenido de la lista entre corchetes, separando cada uno de los elementos mediante una coma

Cada posición de la lista puede contener elementos de distinto tipo

Las listas son mutables, es decir, sus elementos pueden ser modificados

En Python los elementos de una lista se numeran desde 0 hasta longitud – 1

Para acceder al elemento de una lista se pone el nombre de la lista y a continuación el índice al que queremos acceder (si ponemos el índice con signo negativo empezará por el final de la lista)

Para acceder a un rango dentro de una lista tenemos diferentes opciones:

  • Tomar elementos desde el inicio: lista[:a]
  • Tomar elementos desde la posición a (incluida) hasta el final: lista[a:]
  • Tomar elementos desde a hasta b (sin incluir b): lista[a:b]

El inicio del rango siempre incluye el elemento en esa posición, pero no el final del rango

Métodos

Vamos a ver algunos de los métodos para listas de uso más cotidiano

  • append()

    añade un elemento al final de la lista

  • insert()

    se usa para insertar un elemento en el índice asignado

  • pop()

    elimina y devuelve el valor en la posición del índice asignado

  • reverse()

    reordena la lista de forma reversa

  • sort()

    reordena la lista de forma ascendente

Podemos encontrar todos los métodos en su documentación

Tuplas

Las tuplas son similares a las listas, se definen con paréntesis en vez de corchetes

Tienen la peculiaridad de ser inmutables

Como puede verse, se accede a los elementos de igual forma que con las listas

Diccionarios

Los diccionarios definen una relación de uno a uno entre clave valor entre {} y son mutables

Se definen colocando una lista separada por comas de pares clave:valor

Una vez definido, podemos acceder al valor asociado a una clave buscando por clave

Además, podemos buscar si una determinada clave existe o no en nuestro diccionario

Los diccionarios son un tipo de colección en Python que, a diferencia de las listas, están indexadas por palabras y no por números

Los valores pueden ser de cualquier tipo

Podemos pensar en un diccionario como un conjunto no ordenado de pares clave:valor con el requisito de que las claves tienen que ser únicas

Métodos

Vamos a ver algunos de los métodos para diccionarios de uso más cotidiano

  • keys()

    nos devuelve un iterable que contiene las claves del diccionario

  • values()

    nos devuelve un iterable que contiene los valores del diccionario

  • items()

    nos devuelve un iterable con los pares clave:valor del diccionario

Objetos

Los objetos se componen de un conjunto de valores, propiedades y un conjunto de métodos aplicados a esos valores

Son estos métodos los que nos permiten modificar el estado de dicho objeto, es decir, el valor de sus propiedades

En Python los objetos tiene las siguientes particularidades:

  • Todo es un objeto, incluyendo los tipos y clases
  • Permite herencia múltiple
  • No existen métodos ni atributos privados
  • Los atributos pueden ser modificados directamente
  • Permite monkey patching

    Las clases se crean en tiempo de ejecución pero pueden modificarse tras ser creadas

  • Permite duck typing

    El estilo de tipificación dinámica de datos en que el conjunto actual de métodos y propiedades determina la validez semántica, en vez de que lo hagan la herencia de una clase

  • Permite la sobrecarga de operadores
  • Permite la creación de nuevos tipos de datos

Vamos a crear un objeto Universitario de ejemplo en el que tendremos las propiedades: Nombre, Apellido, Edad y Dni

La instancia del objeto la crearemos mediante la asignación a una variable de la siguiente forma:

Es posible consultar la clase de un objeto con la función type, pero también se puede consultar a través de su atributo especial __class__

A su vez las clases tienen un atributo especial __name__ que nos devuelve su nombre en forma de cadena sin adornos:

Es posible inicializar todas las variables para que tengan el tipo que queremos, para ello usaremos el constructor de la clase pasándole los argumentos que necesitemos

El constructor es un método que se llama automáticamente al crear un objeto y se define con el nombre __init__ y mediante la palabra reservada self podremos referenciar al objeto actual

Si existe un constructor también debe existir un destructor que se llame al eliminar el objeto para que encargue de las tareas de limpieza como vaciar la memoria

Todos los objetos se borran automáticamente de la memoria al finalizar el programa, aunque para eliminarlos automáticamente disponemos del método especial __del__

No es aconsejable sobreescribir este método porque se maneja automáticamente, pero es interesante saber que es posible

El método __str__ es el que devuelve la representación de un objeto en forma de cadena

Se llama automáticamente es cuando imprimirmos una variable por pantalla con la función print

Por defecto los objetos imprimen su clase y una dirección de memoria, pero podemos cambiarlo sobreescribiendo su comportamiento

Por ejemplo, para el objeto universitario sobreescribimos el método __str__ para que nos muestre el nombre, edad, apellidos y dni

Un método especial interesante es el que devuelve la longitud

Normalmente está ligado a colecciones, pero nada impide definirlo en una clase y no redefinirlo, porque por defecto no existe en los objetos aunque sea el que se ejecuta al pasarlos a la función __len__

En nuestro ejemplo del objeto universitario no tiene mucho sentido contar su longitud, pero lo incluyo para mostrar su uso

Las propiedades de un objeto pueden describirse mediante otros objetos o incluso colecciones de ellos

La definición de métodos asociados a un objeto puede precisarse en la definición del objeto

Por ejemplo, para el objeto universitario sobreescribimos el método __str__ para que muestre el nombre, edad, apellidos, dni y notas medias del alumno

Para acceder a las propiedades o a los métodos usaremos el operador .

Herencia

La herencia es la capacidad que tiene una clase de heredar los atributos y métodos de otra, algo que nos permite reutilizar código

Para ver su utilidad, vamos a desarrollar un ejemplo modificando el objeto universidad

Partiremos de una clase base que hará de padre (superclase) de otras hijas que heredaran de ella (subclases)

Partimos de una clase Persona que contendrá todos los atributos comunes y dos clases hijas Alumno y Profesor que heredan de ella y tienen atributos o métodos propios

Para heredar los atributos y métodos de una clase en otra sólo tenemos que pasarla entre paréntesis durante su definición

Es posible utilizar el comportamiento de una superclase sin definir nada en la subclase, aunque en nuestro ejemplo si que les daremos comportamiento

Gracias a la flexibilidad de Python podemos manejar objetos de distintas clases masivamente de una forma muy simple

Vamos a empezar creando una lista con nuestros dos Personas de subclases distintas

Uno de los pocos fallos de Python es que si modificamos los valores dentro de un objeto, estos cambios se verán reflejados fuera del mismo

De la misma forma que en las colecciones, los objetos se pasan a las funciones por referencia

Afecta a la hora de hacer copias, creándose en su lugar un acceso al objeto en lugar de uno nuevo con sus valores anteriores

Para realizar una copia a partir de sus valores podemos utilizar la función copy del módulo con el mismo nombre

La función copy se puede utilizar también para copiar colecciones

La herencia múltiple permite a una subclase heredar de múltiples superclases

Esto conlleva un problema, y es que si varias superclases tienen los mismos atributos o métodos, la subclase sólo podrá heredar de una de ellas

Además de superclases también puede heredar de forma múltiple de subclases

En estos casos Python dará prioridad a las clases más a la izquierda en el momento de la declaración de la subclase

Hemos usado la palabra reservada pass para indicarle al intérprete que ignore el código del cuerpo y utilice el de la clase object o el de las superclases (subclases) que le indiquemos

Valor nulo

En Python a las variables se les puede asignar un valor que indica el valor vacío, este valor es el valor NULL

Una variable es considerada None si:

  • se le ha asignado la constante None
  • no se le ha pasado un atributo a una función

La constante None es insensible a mayúsculas o minúsculas