Curso 0: Programación orientada a objetos (POO)

160
P R O G R A M A C I Ó N ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA Curso 0: Programación orientada a objetos (POO) Iván Alduán ([email protected]) 1

Transcript of Curso 0: Programación orientada a objetos (POO)

Page 1: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Curso 0: Programación orientada a objetos (POO)

Iván Alduán ([email protected])

1

Page 2: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Introducción a C++ Introducción al entorno de Visual Studio Programación de pequeños ejemplos en C++

3

Page 3: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Programación

La programación es el proceso de diseñar, escribir, depurar y mantener el código fuente de programas computacionales

Ficheros fuente y programa o código fuente Pensados para que los comprendan los seres humanos Lenguaje de programación de alto nivel: C/C++, Java, C#, …

Ficheros objeto, código objeto y compiladores compilador = traduce el programa fuente a su código objeto equivalente

(un fichero objeto por cada translation unit) Ficheros ejecutables, librerías y enlazadores

Es necesario unir todos los ficheros objeto, más las librerías en un único fichero ejecutable (o librería)

Link o enlazador = combina todos los ficheros que forman nuestro programa y crea el fichero ejecutable

4

Page 4: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Errores

Errores de sintaxis Son errores en el programa fuente. Pueden deberse a palabras

reservadas mal escritas, expresiones erróneas o incompletas El compilador nos dará una lista de errores de sintaxis

Errores de enlazado El programa enlazador también puede encontrar errores,

funciones que no están definidas en ninguno de los ficheros objetos ni en las librerías

Puede que hayamos olvidado incluir alguna librería Errores de ejecución El programa terminará bruscamente Existen programas auxiliares para buscar estos errores, son los

llamados depuradores (debuggers) Errores de diseño

5

Page 5: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

IDEs y Microsoft Visual Studio

Integrated Development Environment Proveen un marco de trabajo amigable con acceso a todas las

herramientas necesarias para desarrollar programas Editor de código

Resaltado de sintaxis, indicador de errores, autocompletado Compilador y Enlazador automáticos

Si fallan te indican el motivo con bastante exactitud Depurador

Ayuda a caminar a través de nuestro programa para detectar errores de ejecución: pila, breakpoint, watch

Constructor de interfaces gráficas WYSIWIG (Plataforma .Net) Microsoft Visual Studio Versión Express gratuita (no plugins :/ ) Versión Professional gratuita a través de DreamSpark

6

Page 6: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

La función main en C++

C++ es un superconjunto de C Aunque existen algunas diferencias entre ambos

int main(): es la función que hace de punto de entrada del programa. Todo programa en C++ debe tener un función main

7

int main(int argc, char *argv[]) { int numero; numero = 2 + 2; return 0; }

Page 7: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Example 01 – Hello World

Comprobando que a todos nos funciona el IDE

8

Page 8: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Tipos de datos fundamentales C++

Heredados de C:

void : no asociado a ningún tipo char : caracter int : entero float : número en coma flotante, precisión simple double : número en coma flotante, doble precisión

Nuevos en C++: bool : tipo booleano wchar_t, char16_t, char32_t : caracter ancho (Unicode)

Librería estándar de C++: std::string : cadenas de caracteres

9

Page 9: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Modificadores de tipos C++

10

Page 10: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Operadores C++

Aritméticos: +, -, *, /, %, : suma, resta, multiplicación, división, resto a++, ++a, a--, --a : postincremento, preincremento, postdecremento

Asignación: x = <<expresión>> : asigna a x el valor de evaluar <<expresión>> +=, -=, *=, /= : suma, resta, multiplicación y división con asignación

Ejemplo: a += b; es equivalente a: a = a + b;

Manejo de bits: &, |, ^, ~ : and, or, xor y not binarios << , >> : desplazamiento a izquierda y a derecha

Lógicos: &&, ||, ! : and, or, not (devuelven un bool)

11

Page 11: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Operadores C++

Relacionales: >, >=, <, <=, ==, != : mayor, mayor o igual, menor, menor o igual, .. (devuelven un bool)

de Preproceso: #define, #line, #pragma ….

de Puntero: Operadores de indirección (*) y de referencia (&)

Manejo de memoria: new y delete

Otros: :: , .* , ->* , ? : , sizeof(), typeid() ....

12

Page 12: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Operadores C++

Precedencia Prioridad de unos

operadores frente a otros Puede modificarse con

paréntesis

Asociatividad define el orden de

ejecución para operadores con idéntica precedencia

13

Page 13: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Sentencias C++

Expresiones Declaración de variables <tipo> <identificador>; Asignación <variable> = <expresion>; Llamada a función <funcion>(<lista_parametros>);

Bucles for (<inicializacion>; <condicion>; <incremento>) <sentencia> while (<condicion>) <sentencia> do <sentencia> while (<condicion>)

Selección if (<condicion>) <sentencia1> else <sentencia2> switch (<variable) case <expresion>: <sentencia>

14

Page 14: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Example 02 – Múltiplos de 3

Usando diferentes tipos de sentencias

15

Page 15: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Funciones C++

En C++ es obligatorio usar prototipos. Un prototipo es una declaración de una función antes de ser utilizada dicha función

Las funciones se deben definir en alguna parte, implementando su funcionalidad (cuerpo) Pueden estar en librerías externas, otros ficheros fuentes, etc

16

//Declaración de la función int media(int, int); ... //Definición de la función int media(int a, int b) { int result; result = (a + b)/2; return result; }

Page 16: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Funciones C++

La estructura de un programa en C++ quedaría así

17

Page 17: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Funciones C++ Recursividad

Una función es recursiva si durante su ejecución tiene una llamada a si misma

Se distingue entre: Recursividad directa Recursividad indirecta: varias se llaman unas a otras

formando ciclos Toda función recursiva ha de presentar al menos una

condición de terminación Ejemplos: Cálculo del factorial mediante recursividad directa

18

Page 18: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Example 03 – Factorial

Usando funciones, el debugger y la pila de llamadas

19

Page 19: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ámbito de variables y funciones

Una variable es global si se declara fuera de cualquier función. Se puede acceder a ella desde cualquier función Una variable global estática sólo es visible en la unidad de

compilación en la que se declara

Las variables locales se declaran dentro de una función o bloque, y solo son visibles desde el bloque donde se declaran Los parámetros de una función son variables locales Una variable local estática conserva el valor entre distintas

llamadas a la función

20

Page 20: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ámbito de variables y funciones

21

/* Variables globales */ int i; int j = 10; float k, l; static char m; static int funcion_1() { /* Variables locales */ char d = ‘A’; static int call = 0; … call++; … return call; }

Page 21: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Conversión de tipos

Implícita: En expresiones el tipo mas bajo promociona al mas alto

long double > double > float > unsigned long long > long long > unsigned long > long > unsigned int > int > unsigned short > short > unsigned char > char

En asignaciones el valor del lado derecho se convierte al tipo de la variable de la izquierda

Explicita (casting) (tipo) expresion

22

Page 22: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Constantes C++

Varias formas de declararlas: Usando la directiva del preprocesador #define: #define MAX_SIZE 64

Usando un tipo enumerado: enum{

MAX_SIZE = 64,

};

Usando const : const int MAX_SIZE = 64;

23

Page 23: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Arrays C/C++

Son variables que contienen una colección consecutiva de datos

Se declaran entre corchetes, y su tamaño debe ser fijado en tiempo de compilación

Se accede a los elementos también entre corchetes. Los índices comienzan en 0, y no hay comprobación

24

int a[10]; //array de 10 ints float b[2][10] //array de 2 dimensiones . . . a[0] = 10; b[1][4] = 5.3; a[20] = 123; //esto no da error de compilación

Page 24: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Inicialización de Arrays

Al declarar un array se le puede dar valores iniciales a sus elementos:

Si no se especifica el tamaño, tomará el del número

de elementos inicializados. Si se inicializan menos del tamaño, los no

inicializados tendrán basura. Si se inicializan más del tamaño, el compilador dará

un aviso. 25

int a[4] = {13, 1, 27, 1289}; int b[] = {1, 3, 5, 7, 9}; int c[4] = {23, 12}; //c[2] y c[3] sin inicializar int d[2] = {12, 24, 91, 103}; //warning

Page 25: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Punteros C/C++

Un puntero es una variable que representa una posición de memoria que contiene un dato

Se declaran anteponiendo un * al nombre de la variable.

Admiten el valor NULL (definido en cstdlib)

26

int *a; // puntero a entero float *b; // puntero a flotante char *c; // puntero a caracter

Page 26: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Operadores de punteros

Operaciones: El operador * dereferencia el puntero. Es decir, se accede

al valor apuntado El operador & devuelve la dirección de memoria donde se

encuentra una variable. Es decir se obtiene un puntero a la variable

27

int a = 0; int *b; b = &a; // b apunta a la dirección donde está a *b = 127; // se guarda 127 en la dir. apuntada por b //En este punto la variable a tiene valor 127

Page 27: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Operadores de punteros

Operaciones: Los punteros se pueden sumar, restar, etc Esas operaciones se hacen en múltiplos del tamaño del

dato apuntado

28

int *a = . . . . //a apunta a algún lugar a = a + 1; //ahora apunta sizeof(int) más adelante // a apunta a la dir. del siguiente int en memoria a = a + 4; //ahora apunta 4*sizeof(int) más adelante

Page 28: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Arrays y punteros

Los arrays se pueden comportar como punteros, y los punteros como arrays

Una variable de tipo array es un puntero al primer elemento del array

Un puntero al primer elemento de una colección consecutiva puede usarse como un array

29

int a[16]; //array de 16 elementos *a = 10; // Es lo mismo que a[0] = 10; *(a + 3) = 20; // Es lo mismo que a[3] = 20; int *b = (int *) malloc (8*sizeof(int)); //b es un puntero a un espacio de memoria en el //que caben 8 ints b[6] = 123; // Es lo mismo que *(b + 6) = 123;

Page 29: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Arrays y punteros

Diferencias: Un array tiene un tamaño asociado, un puntero no Un array es como un puntero constante, no se puede

cambiar el lugar al que apunta Un array está definido en memoria estática y un puntero

puede apuntar a memoria dinámica

30

int a[16]; //array de 16 elementos int s1 = sizeof(a); //s1 valdrá 16*sizeof(int) int *b = (int *) malloc (128*sizeof(int)); //b es un puntero a una colección de 128 int int s2 = sizeof(b); //s2 valdrá 4 u 8, que es el //tamaño de una dirección

Page 30: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Memoria dinámica

Stack o Pila (Memoria estática) Variables locales (dentro de un bloque) Va aumentando acumulando bloques de variables encima a

medida que entramos a más funciones El programa la gestiona automáticamente (FIFO) Tamaño muy limitado (1MB – 32MB)

Heap o Montículo (Memoria dinámica) Grueso de memoria no utilizado por ningún programa Podemos reservar memoria dinámicamente Enorme cantidad de memoria Tenemos que gestionarla los programadores

31

Page 31: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

malloc y free (C/C++)

Ejemplo:

32

int *a, *b; // punteros a enteros //se reserva espacio en memoria para un entero //a apunta a ese espacio de memoria a = (int *) malloc (1*sizeof(int)); //se reserva espacio en memoria para 16 enteros //b apunta a ese espacio de memoria b = (int *) malloc (16*sizeof(int)); //se libera el espacio del primer malloc free(a); //se libera el espacio del segundo malloc free(b);

Page 32: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

new y delete (C++)

Para realizar esta administración de la memoria dinámica, C++ cuenta con dos operadores new y delete

El operador new reserva memoria dinámica para cualquier tipo tipos primitivos (int, double) tipos definidos por el usuario (clases o registros)

delete se encarga de liberar la memoria previamente reservada Pueden aplicarse para reservar elementos individuales o arrays

33

int *a, *b; a = new int; b = new int[100000000]; delete a; delete[] b;

Page 33: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Example 04 – Ordenación de un vector

Usando watch para inspeccionar el valor de punteros

34

Page 34: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Registros C++

Son tipos compuestos formados por elementos heterogéneos

Dentro del registro cada elemento tiene un identificador y un tipo.

35

//Definición del registro struct Complejo { float real; float imag; }; //Declaración de variables del tipo registro Complejo uncomplejo, otrocomplejo;

Page 35: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Registros C++

Para acceder a los elementos de un registro estructura se utiliza el operador punto (.)

Si se trata de un puntero a registro se puede atajar con el operador flecha (->)

36

uncomplejo.real = 1.3; uncomplejo.imag = 2.7;

Complejo *a = (Complejo *)malloc(sizeof(Complejo)); a->real = 2.4; //lo mismo que (*a).real = 2.4; a->imag = 3.14; //lo mismo que (*a).imag = 3.14;

Page 36: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

std::strings (C++)

En C++ si existe un tipo de datos para strings También se utilizan arrays de char acabados con el

caracter ‘\0’ como en C Una cadena de caracteres entre comillas dobles es un

inmediato que representa un string

37

#include<cstring> std::string s = “Esto es un tipo cadena”; char s1[] = “Hola”; char *s2 = “Hola”; char *s3[] = {‘H’, ‘o’, ‘l’, ‘a’, ‘\0’} std::string s4(s1); // convertir a string int n = s4.length(); // longitud de la cadena

Page 37: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Argumentos de funciones (C++)

Los argumentos por defecto siempre se pasan por valor Pasar un argumento por valor copia todo su contenido No se deben pasar nunca objetos pesados por valor Podríamos pasar punteros a los objetos

Con paso por referencia la sintaxis es mucho más amigable sin tener que aplicar los operadores de punteros Internamente funcionan como punteros

38

//Ejemplo de paso de argumentos por referencia void intercambia(int &a, int &b) { int aux = a; a = b; b = aux; } int x = 10, y = 20; Intercambia(x, y);

Page 38: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Example 05 – Palíndromos

Operando con std::string

39

Page 39: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Espacios con nombre (C++)

Nos ayudan a evitar problemas con identificadores iguales en grandes proyectos Diferentes librerías puede que usen los mismos nombres

para cosas diferentes, de modo que resulta imposible integrar esas librerías en la misma aplicación

40

namespace mathlib { int max(int a, int b); int min(int a, int b); struct Vector { float x, y, z; }; ... }

Page 40: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Espacios con nombre (C++)

El nombre del espacio funciona como un prefijo para las variables, funciones o clases declaradas en su interior

Para acceder a una de esas variables se tiene que Usar un especificador de ámbito (::) activar el espacio con nombre adecuado

41

mathlib::vector v; int n = mathlib::max(10, 15); using namespace mathlib; Vector w; int m = min(10, 15);

Page 41: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Librerías externas en Windows

Una librería es un conjunto de recursos (algoritmos) prefabricados, que pueden ser utilizados por el programador para realizar determinadas operaciones

Windows: librerías estáticas (.lib) y librerías dinámicas (.dll) MSBUILD: librerías de importación (.lib)

Necesitamos tres cosas Archivos de definición o includes Las librerías a importar dentro de nuestro programa (.lib) Si procede, que el programa tenga acceso a la librería dinámica

cuando entre en ejecución (.dll) Mismo directorio que el ejecutable PATH del sistema operativo

42

Page 42: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Example 06 – GLUT Cube

Usando librerías externas y pintando gráficos 3D

43

Page 43: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Bibliografía recomendada

S.B. Lippman – C++ Primer (5th) – 2012 B. Stroustrup – The C++ Programming Language (4th) – 2013

44

Page 44: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Programación orientada a objetos (POO)

45

Page 45: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Programación Orientada a Objetos

La programación orientada a objetos es una forma de programar que trata de encontrar una solución más intuitiva para la resolución de problemas complejos

Exige un cambio de mentalidad para diseñar aplicaciones y programas informáticos ahora más complejos No buscamos directamente el encontrar la secuencia exacta de las

instrucciones necesarias para resolver el problema Queremos abstraernos a un nivel más conceptual para dividir el problema

en una serie de elementos que interaccionando entre sí den solución al problema

La idea básica de este tipo de programación es agrupar los datos y los procedimientos para manejarlos en entidades únicas con un significado a las que llamaremos objetos

Un programa es un objeto, que a su vez está formado de otros objetos que interactúan entre sí

46

Page 46: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Objeto

Un objeto es una unidad con cierto significado que engloba en sí mismo: Un conjunto de datos que definen su estado Los procedimientos necesarios para el tratamiento de esos

datos con facilidad Ejemplos de objetos del inundo real son: pasajero,

asiento, avión, vuelo, aeropuerto Por ejemplo, los atributos de un pasajero incluyen el nombre, la

edad, el sexo, la fecha de nacimiento, la dirección, etc El comportamiento es el conjunto de cosas que puede hacer un

objeto; por ejemplo, un pasajero puede estudiar, trabajar, comer, dormir, etc

47

Page 47: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Objeto

Posible ejemplo de un objeto dentro de una aplicación encargada de gestionar unos cines

Otros objetos en la aplicación podrían ser cine, empleado, sala, proyector, butaca, espectador, entrada

48

Page 48: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Objeto: conceptos

Propiedades o atributos: Características o variables que definen a un objeto

Métodos: Funciones disponibles en el objeto para manipular o modificar los atributos del mismo

Mensaje: El mensaje es el modo en el que se comunican los objetos entre sí En realidad, esto no es mas que una llamada a un método

de un determinado objeto

49

Page 49: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Programa OO vs OP

El resultado final del proceso es un programa de computadora que contiene características que representan algunos de los objetos del mundo real que son parte del suceso

50

Page 50: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ventajas

Ventajas de la programación orientada a objetos Diseños más cercanos al mundo real Más fáciles de diseñar y mantener Facilidad de comunicación entre todos los roles implicados

en el desarrollo: usuarios, clientes, analistas, diseñadores, programadores

Facilita la reutilización de código ya que cada objeto tiene significado propio Cada objeto es independiente del resto Ejemplo: Una clase Vector3 la podremos reutilizar en todas

nuestras aplicaciones de gráficos

51

Page 51: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Clases

Una clase define un patrón para construir objetos Es importante distinguir entre objetos y clases La clase es simplemente una declaración, patrón o tipo Los objetos son los ejemplares concretos de una clase.

Cuando creamos un ejemplar tenemos que especificar la clase a partir de la cual se creará Por ejemplo, un objeto de la clase película sería Toy Story

52

Page 52: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Clases en C++

Las clases C++ permiten definir nuevos tipos de datos Cada clase es un nuevo tipo Cada elemento de la clase se caracteriza por ciertos valores

y las operaciones disponibles para crear dichos elementos, modificarlos y destruirlo

Podemos establecer un paralelismo entre los tipos de datos vistos hasta el momento (int, char, array, struct, …) y las clases Ambos son tipos Pueden declararse elementos de ese tipo

En los tipos por defecto los llamábamos variables En el caso de una clase los llamaremos instancias u objetos

53

Page 53: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Clases en C++

Características fundamentales de las clases en C++

Nombre de la clase. Sirve para identificar a todos los objetos que tengan unas determinadas características

Conjunto de atributos. Datos miembro. El valor de los atributos representan el estado de cada objeto.

Conjunto de métodos. Funciones miembro. Permite que los objetos cambien de estado, dependiendo del estado anterior que tuviera el objeto.

Niveles de acceso para proteger ciertos miembros de la clase. Normalmente, se definirán como ocultos (privados) los atributos y visibles (públicos) los métodos.

54

Page 54: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Declaración de clases en C++

55

Page 55: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Paso de mensajes

56

Una vez creados los objetos, podemos trabajar con ellos. Si queremos que un determinado objeto ejecute un método, utilizamos el operador punto (•).

A esto se le conoce como paso de mensajes. Cada paso de mensaje provoca la ejecución del correspondiente

método definido en la clase del objeto receptor Cada objeto entiende tantos mensajes como métodos estén definidos

en su clase

Page 56: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ocultación / Encapsulamiento

La clave de la programación orientada a objetos es el encapsulamiento de todo el código y detalles de implementación bajo interfaces de manejo sencillo

La definición de una clase en C++ viene dada por: Un archivo de cabecera (.h)

Define la interfaz de la clase de forma clara, es decir, qué métodos ofrece el módulo definido, sin detalles de implementación

Un archivo fuente (.cpp) Define los detalles de implementación de la clase Inclusión de su correspondiente fichero de cabecera (#include) Definición de funciones declaradas y no declaradas en el fichero

de cabecera

57

Page 57: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Especificadores de acceso

Dentro de la lista de miembros, cada miembro puede tener diferentes niveles de acceso

Public: miembros accesibles desde cualquier parte Private: sólo son accesibles por la propia clase Protected: nos faltan conocimientos para entenderlo

58

class <identificador de clase> { public: <lista de miembros> private: <lista de miembros> protected: <lista de miembros> };

Page 58: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Especificadores de acceso

Por lo general Los atributos deben ser privados Los métodos o funciones miembro deben ser públicas A través del objeto de una clase sólo se puede acceder a lo que está

declarado como público en la clase Lo privado solo puede ser manipulado internamente desde el código

de los métodos

59

Page 59: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

El puntero this

Todos los objetos de una clase comparten la misma copia de las funciones de esa clase ¿cómo hace una función miembro para referirse a un dato

de un objeto en concreto?

La respuesta es: usando el puntero this cada objeto tiene asociado un puntero a si mismo que se

puede usar para manejar sus miembros generalmente su uso es transparente al programador, pero

a veces es necesario invocarlo de manera explícita

60

void pareja::Guarda(int a_input, int b) { a = a_input; // equivale a this->a = a_input; this->b = b;

}

Page 60: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Diseño conceptual

Para representar gráficamente las clases y objetos, se utilizan diagramas conceptuales basados en UML (Lenguaje de Modelado Unificado)

61

Page 61: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Resumen

Las instancias de un tipo cualquiera se denominan variables, mientras que las instancias de una clase se denominan objetos

Los atributos describen el estado de un objeto. Un atributo consta de dos partes: nombre del atributo y valor.

Los métodos describen el comportamiento de los objetos de una clase. Representan las operaciones que se pueden realizar con los objetos de la clase. La ejecución de un método puede conducir a cambiar el estado del objeto.

Los objetos se manipulan mediante el paso de mensajes. Para ejecutar un método asociado a un objeto, se realiza una acción que se conoce como “envío de mensajes”.

Se denomina encapsulamiento al ocultamiento del estado, es decir, de los datos miembro, de un objeto Las operaciones y datos visibles desde el exterior de la clase es lo que

se denomina interfaz de la clase

62

Page 62: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

El poder de la POO

Constructores y destructores Sobrecarga de operadores y métodos Métodos estáticos Herencia Interfaces Clases abstractas Funciones virtuales

Polimorfismo Plantillas Excepciones

63

Page 63: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Constructores

Los constructores son funciones miembro especiales que sirven para inicializar un objeto

Tienen el mismo nombre que la clase, no retornan ningún valor y no pueden ser heredados

Por norma general deben ser públicos ya que siempre se usan desde el exterior de la clase en un patrón de diseño singleton precisamente nos

interesa lo contrario, que el constructor esté oculto

Si no declaramos ningún constructor, el compilador lo hará por nosotros creando uno por defecto

64

Page 64: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Constructores

Ejemplo:

65

class pareja { public:

// Constructor pareja(int a2, int b2); // Funciones miembro de la clase "pareja" void Lee(int &a2, int &b2); void Guarda(int a2, int b2);

private: // Datos miembro de la clase "pareja" int a, b;

public: }; pareja::pareja(int a2, int b2) {

a = a2; b = b2;

}

Page 65: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Constructores

Cuando se use un constructor sin parámetros para declarar un objeto no se deben escribir los paréntesis error frecuente cuando se empiezan a usar clases

Si un constructor requiere argumentos, es obligatorio suministrarlos

66

pareja par1(12,43); pareja par2(45,34); pareja par1(); //ERROR -> El compilador piensa que es un //prototipo de una función pareja par1;

Page 66: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Constructores

Hay un modo más seguro de inicializar los datos miembros de los objetos en los constructores Inicializadores: Cada inicializador consiste en el nombre de

la variable miembro a inicializar, seguida de la expresión que se usará para inicializarla entre paréntesis

Pregunta: ¿Qué pasa si dentro de nuestra clase tenemos como

atributo un objeto sin constructor por defecto? ¿Eficiencia?

67

pareja::pareja(int a2, int b2) : a(a2), b(b2) {}

Page 67: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Constructores

Sobrecarga de constructores podemos definirse varios constructores para cada clase

Argumentos por defecto reducir el número de constructores necesarios

68

pareja(int a2, int b2) : a(a2), b(b2) {} pareja() : a(0), b(0) {}

pareja(int a2=0, int b2=0) : a(a2), b(b2) {}

Page 68: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Constructores

Constructor copia crea un objeto a partir de otro objeto existente un argumento que es una referencia a un objeto de su

misma clase si no se define, el compilador crea uno por defecto

Asignación de objetos copia los valores de los datos miembro

69

pareja(const pareja &p); pareja::pareja(const pareja &p) : a(p.a), b(p.b) {}

pareja par1(12, 32), par2; par2 = par1;

Page 69: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Destructores

Los destructores son funciones miembro especiales que sirven para definir cómo se elimina un objeto de una determinada clase

Tienen el mismo nombre que la clase, pero con el símbolo ~ delante, no retornan ningún valor y no pueden ser heredados

En general, será necesario definir un destructor cuando nuestra clase tenga datos miembro de tipo puntero

Pregunta: ¿Tiene sentido la sobrecarga de destructores?

70

Page 70: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ejemplo: Clase cadena

71

class cadena { public:

cadena(char *c); cadena(const cadena &); // ¿Por qué es necesario definirlo? ~cadena(); // ¿Por qué es necesario definirlo? void Set(char *dest); char* Get();

private: char *cad; // cadena de caracteres

}; cadena::cadena(char *c) {

cad = new char[strlen(c)+1]; strcpy(cad, c); // Almacena la cadena

} …

Page 71: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ejemplo: Clase cadena

72

… cadena::~cadena() {

delete[] cad; // Libera la memoria reservada a cad } cadena::cadena(const cadena &c) {

if(&c == this) { cout << "Sí, soy yo." << endl; this->cad = c.cad;

} else {

cout << "No, no soy yo." << endl; this->cad = new char[strlen(c.cad)+1]; strcpy(this->cad, c.cad);

} return c;

}

Page 72: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Operadores sobrecargados

Podemos redefinir cualquier operando aplicado a una clase para que funcione como nosotros deseemos

Cuando se sobrecargan operadores en el interior de una clase se asume que un operando es el propio objeto de la clase por lo que no hay que declararlo

Cuando nuestra clase tenga punteros es posible que necesitemos sobrecargar el operador asignación (=) Pensar en los problemas anteriores del constructor copia

por defecto

73

Page 73: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Sobrecarga de operadores

74

class Tiempo { public: Tiempo(int h=0, int m=0) : hora(h), minuto(m) {} Tiempo operator+(const Tiempo &h); Tiempo operator*(const Tiempo &h); ¿tiene sentido? private: int hora; int minuto; }; Tiempo Tiempo::operator+(const Tiempo &h) { Tiempo temp; temp.minuto = minuto + h.minuto; temp.hora = hora + h.hora; if(temp.minuto >= 60) { temp.minuto -= 60; temp.hora++; } return temp; }

Page 74: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Operadores sobrecargados

Problema: ¿Cómo sobrecargamos un operador unitario sufijo?

75

class Tiempo { ... Tiempo& operator++(); ...

}; Tiempo& Tiempo::operator++() {

minuto++; while(minuto >= 60) {

minuto -= 60; hora++;

} return *this;

} Tiempo t1; ++t1; ¿t1++;?

Page 75: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Operadores sobrecargados

Problema: ¿Cómo sobrecargamos el operador unitario sufijo? no hay forma de decirle al compilador cuál de las dos

modalidades del operador estamos sobrecargando, así que los compiladores usan una regla: si se declara un parámetro para un operador ++ ó – se sobrecargará la forma sufija del operador

76

Tiempo Tiempo::operator++(int) { Tiempo temp(*this); // Constructor copia minuto++; while(minuto >= 60) {

minuto -= 60; hora++;

} return temp;

}

Page 76: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Métodos sobrecargados

Sobrecarga de métodos Las funciones miembros de las clases también pueden

sobrecargarse

Argumentos por defecto En las funciones miembros de las clases también pueden

usarse parámetros con valores por defecto

77

void Vector3D::Asignar(float xi, float yi=0, float zi=0) { x = xi; y = yi; z = zi;

} void Vector3D::Asignar(const Vector3D &p) {

Asignar(p.x, p.y, p.z); }

Page 77: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Sistema de protección

Especificadores de acceso public: private: protected:

Declaraciones friend El modificador "friend" puede aplicarse a clases o funciones

para inhibir el sistema de protección Las relaciones de "amistad" entre clases son parecidas a las

amistades entre personas: la amistad no puede transferirse, si A es amigo de B, y B es

amigo de C, esto no implica que A sea amigo de C la amistad no puede heredarse. Si A es amigo de B, y C es una

clase derivada de B, A no es amigo de C la amistad no es simétrica. Si A es amigo de B, B no tiene por

qué ser amigo de A 78

Page 78: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Sistema de protección

Ejemplo: funciones amigas externas

79

class A { public:

A(int i=0) : a(i) {}

private: int a; friend void Ver(A); // "Ver" es amiga de la clase A

}; void Ver(A Xa) {

// La función Ver puede acceder a miembros privados // de la clase A, ya que ha sido declarada "amiga" de A cout << Xa.a << endl;

}

Page 79: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Sistema de protección

Ejemplo: funciones amigas en otras clases

80

class A; // Declaración previa (forward) class B { public:

B(int i=0) : b(i) {} void Ver() { cout << b << endl; } bool EsMayor(A Xa); // Compara b con a

private: int b;

}; class A { public:

A(int i=0) : a(i) {} void Ver() { cout << a << endl; }

private: // Función amiga tiene acceso a miembros privados de la clase A friend bool B::EsMayor(A Xa); int a;

};

Page 80: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Sistema de protección

Ejemplo: clases amigas

81

/* Clase para elemento de lista enlazada */ class Elemento { public:

Elemento(int t); int Tipo() { return tipo;}

private: int tipo; Elemento *sig; // siguiente elemento friend class Lista; // amistad con lista

}; /* Clase para lista enlazada de números*/ class Lista {

. . . }

Page 81: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Modificadores de miembros

Funciones miembro inline El código generado para esa función cuando el programa se

compila, se inserta en todos los punto donde se invoca a la función, en lugar de hacerlo en otro lugar y hacer llamadas

Hay dos maneras de declarar una función como inline: Las funciones que se definen dentro de la declaración de la clase

son inline implícitamente La otra forma es hacerlo explícitamente

82

class Ejemplo { public:

Ejemplo(int a = 0); private:

int A; }; inline Ejemplo::Ejemplo(int a) : A(a) {}

Page 82: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Modificadores de miembros

Funciones miembro const Cuando una función miembro no modifique el valor de

ningún dato de la clase, podemos y debemos declararla como constante

si la función intenta modificar el objeto el compilador generará un error

83

class Ejemplo2 { public:

Ejemplo2(int a = 0) : A(a) {} void Modifica(int a) { A = a; } // Error si se declara constante int Lee() const { return A; }

private: int A;

};

Page 83: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Modificadores de miembros

Otros usos de const valores de retorno constantes de las funciones paso de parámetros constantes a funciones

84

const Vector Vector::operator+( const Vector &other ) const { Vector result; result.x = this->x + other.x; result.y = this->y + other.y; result.z = this->z + other.z; return result;

}

Page 84: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Modificadores de miembros

Miembros static de una clase Son miembros que no dependen de un objeto o instancia

concreto sino que funcionan a nivel de clase En el caso de los atributos static sólo existirá una copia que

compartirán todos los objetos de la misma clase Es necesario inicializar los datos estáticos de una clase

Las funciones static no pueden acceder a los miembros de los objetos, sólo pueden acceder a los datos miembro de la clase que sean static

85

Page 85: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Modificadores de miembros

Ejemplo:

86

class Singleton { public: static Singleton* Instance(); private: Singleton(); Singleton(const Singleton &); Singleton &operator= (const Singleton &); static Singleton* pinstance; }; Singleton* Singleton::pinstance = NULL;// Inicializa el miembro static Singleton* Singleton::Instance () {

if (pinstance == NULL) // ¿Es la primera llamada? pinstance = new Singleton; // Creamos la instancia

return pinstance; } Singleton *obj = Singleton::Instance();

Page 86: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Example 07 – GLUT orientado a objetos

87

Page 87: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Herencia

Nos permite crear nuevas clases a partir de clases existentes, conservando las propiedades de la clase original y añadiendo otras nuevas

La nueva clase obtenida se conoce como clase derivada, y las clases a partir de las cuales se deriva, clases base cada clase derivada puede usarse como clase base para

obtener una nueva clase derivada y cada clase derivada puede serlo de una o más clases base

88

Page 88: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Herencia

Esto nos va a permitir crear jerarquías de clases tan complejas como nos sea necesario

89

Page 89: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Herencia

Un ejemplo muy común es de las personas todas las personas tienen propiedades comunes, nombre,

fecha de nacimiento, género, estado civil, etc. dividimos a todas las personas en dos grandes clases:

empleados y estudiantes los ingresos por nómina son exclusivos de los empleados la nota media del curso es exclusiva de los estudiantes ahora podemos clasificar a los empleados en ejecutivos y

comerciales ….

90

Page 90: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Herencia

Ahora podemos ver las ventajas de disponer de una jerarquía completa de clases Cada vez que creemos un objeto de cualquier tipo

derivado este tendrá las propiedades de todos sus tipos base

Siempre podremos crear nuevas clases para resolver nuevas situaciones

Podemos aplicar procedimientos genéricos a una clase en concreto sin tener en cuenta que tipo de subclase es

91

Page 91: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Herencia

Ejemplo:

92

// Clase base Persona: class Persona { public:

Persona(char *n, int e); const char *LeerNombre(char *n) const; int LeerEdad() const; void CambiarNombre(const char *n); void CambiarEdad(int e);

protected: char nombre[40]; int edad;

}; // Clase derivada Empleado: class Empleado : public Persona { public:

Empleado(char *n, int e, float s); float LeerSalario() const; void CambiarSalario(const float s);

protected: float salarioAnual;

};

Page 92: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Herencia

Para cada clase base podemos definir dos tipos de acceso, public o private. Si no se especifica ninguno de los dos, por defecto se asume que es private public: los miembros heredados de la clase base conservan el

tipo de acceso con que fueron declarados en ella private: todos los miembros heredados de la clase base pasan a

ser miembros privados en la clase derivada

Usar el acceso protected nos permite que los datos sean inaccesibles desde el exterior de las clases, pero a la vez, permite que sean accesibles desde las clases derivadas

93

Page 93: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Herencia

Constructores en clases derivadas Cuando se crea un objeto de una clase derivada, primero

se invoca al constructor de la clase base y a continuación al constructor de la clase derivada Si el constructor base no tiene parámetros la llamada se

realiza de forma automática Si el constructor base necesita parámetros, tenemos que

encargarnos nosotros de llamar al constructor base

94

Page 94: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Herencia

Ejemplo:

95

class ClaseA { public:

ClaseA(int a) : datoA(a) { cout << "Constructor de A" << endl; } int LeerA() const { return datoA; }

protected: int datoA;

}; class ClaseB : public ClaseA { public:

ClaseB(int a, int b) : ClaseA(a), datoB(b) { (1) cout << "Constructor de B" << endl; } int LeerB() const { return datoB; }

protected: int datoB;

};

Page 95: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Herencia

Destructores en clases derivadas Cuando se destruye un objeto de una clase derivada,

primero se invoca al destructor de la clase derivada, si existen objetos miembro a continuación se invoca a sus destructores y finalmente al destructor de la clase base

96

class ClaseB : public ClaseA { public:

ClaseB() : datoB(20) { cout << "Constructor de B" << endl; } ~ClaseB() { cout << "Destructor de B" << endl; } int LeerB() const { return datoB; }

protected: int datoB;

};

Page 96: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Polimorfismo

En una clase derivada se puede definir una función que ya existía en la clase base, esto se conoce como "overriding", o superposición de una función La definición de la función en la clase derivada oculta la

definición previa en la clase base Podemos acceder a la función de la clase base mediante

una sintaxis un tanto especial

Superposición Cuando se superpone una función, se ocultan todas las

funciones con el mismo nombre en la clase base 97

Page 97: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Polimorfismo

Ejemplo:

98

class ClaseA { public:

ClaseA() : datoA(10) {} int LeerA() const { return datoA; } void Mostrar() { cout << "a = " << datoA << endl; }

protected: int datoA;

}; class ClaseB : public ClaseA { public:

ClaseB() : datoB(20) {} int LeerB() const { return datoB; } void Mostrar() { cout << "a = " << datoA << ", b = “ << datoB << endl; }

protected: int datoB;

}; ClaseB objeto; objeto.Mostrar(); objeto.ClaseA::Mostrar();

Page 98: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

C++ nos permite acceder a objetos de una clase derivada usando un puntero a la clase base

Por supuesto, sólo podremos acceder a datos y funciones que existan en la clase base, los datos y funciones propias de los objetos de clases derivadas serán inaccesibles

Con lo que hemos visto hasta ahora, si accedemos a objetos de una clase derivada usando un puntero a la clase base, se ejecuta el código de la clase base

99

Polimorfismo

Page 99: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Polimorfismo

Ejemplo:

100

class Persona { public:

Persona(char *n) { strcpy(nombre, n); } void VerNombre() { cout << nombre << endl; }

protected: char nombre[30];

}; class Empleado : public Persona { public:

Empleado(char *n) : Persona(n) {} void VerNombre() { cout << "Emp: " << nombre << endl; }

}; class Estudiante : public Persona { public:

Estudiante(char *n) : Persona(n) {} void VerNombre() { cout << "Est: " << nombre << endl; }

}; Persona *Pepito = new Estudiante("Jose"); Persona *Carlos = new Empleado("Carlos");

Page 100: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Polimorfismo

Sería mucho más interesante que cuando se invoque a una función que se superpone en la clase derivada, se llame a ésta última función, la de la clase derivada

Esto se consigue mediante el uso de funciones virtuales cuando en una clase declaramos una función como virtual,

y la superponemos en alguna clase derivada, al invocarla usando un puntero de la clase base, se ejecutará la versión de la clase derivada

101

Page 101: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Polimorfismo

Ejemplo:

102

class Persona { public:

Persona(char *n) { strcpy(nombre, n); } virtual void VerNombre() { cout << nombre << endl; }

protected: char nombre[30];

}; class Empleado : public Persona { public:

Empleado(char *n) : Persona(n) {} void VerNombre() { cout << "Emp: " << nombre << endl; }

}; class Estudiante : public Persona { public:

Estudiante(char *n) : Persona(n) {} void VerNombre() { cout << "Est: " << nombre << endl; }

}; Persona *Pepito = new Estudiante("Jose"); Persona *Carlos = new Empleado("Carlos");

Page 102: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Polimorfismo

También funciona con referencias

Una vez que una función es declarada como virtual, lo seguirá siendo en las clases derivadas, es decir, la propiedad virtual se hereda

103

Estudiante Pepito("Jose"); Empleado Carlos("Carlos"); Persona &rPepito = Pepito; // Referencia como Persona Persona &rCarlos = Carlos; // Referencia como Persona rCarlos.VerNombre(); rPepito.VerNombre();

Page 103: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Polimorfismo

1. Supongamos que tenemos una estructura de clases en la que en alguna de las clases derivadas exista un destructor…

2. si destruimos un objeto referenciado mediante un puntero a la clase base, y el destructor no es virtual, estaremos llamando al destructor de la clase base…

3. ¡Esto puede ser desastroso!

Destructores virtuales debemos respetar siempre ésta regla: si en una clase

existen funciones virtuales, el destructor debe ser virtual

104

Page 104: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Polimorfismo

1. accedemos a un objeto de una clase derivada usando una referencia a la clase base …

2. llamamos al constructor copia para crear una nueva copia de esa clase…

3. ¡Estamos llamando al constructor copia de la clase base para copiar una clase derivada!

Constructores virtuales Los constructores no pueden ser virtuales Si un constructor llama a una función virtual, ésta será siempre

la de la clase base (la clase derivada aún no se ha creado) Para solucionar este inconveniente se suele crear una función

virtual "clonar" en la clase base que se superpondrá para cada clase derivada

105

Page 105: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Polimorfismo

Ejemplo:

106

class Persona { public:

Persona(char *n) { strcpy(nombre, n); } Persona(const Persona &p); virtual Persona* Clonar() { return new Persona(*this); }

protected: char nombre[30];

}; class Empleado : public Persona { public:

Empleado(char *n) : Persona(n) {} Empleado(const Empleado &e); virtual Persona* Clonar() { return new Empleado(*this); }

}; class Estudiante : public Persona { public:

Estudiante(char *n) : Persona(n) {} Estudiante(const Estudiante &e); virtual Persona* Clonar() { return new Estudiante(*this); }

};

Page 106: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Clases abstractas

Funciones virtuales puras Una función virtual pura es aquella que no necesita ser

definida El modo de declarar una función virtual pura es

asignándole el valor cero

107

class Persona { public:

Persona(char *n) { strcpy(nombre, n); } virtual void Mostrar() = 0;

protected: char nombre[30];

};

Page 107: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Clases abstractas

Clase abstracta Una clase abstracta es aquella que posee al menos una

función virtual pura No es posible crear objetos de una clase abstracta, estas

clases sólo se usan como clases base para la declaración Las funciones virtuales puras serán aquellas que siempre

se definirán en las clases derivadas, de modo que no se necesita implementación base

Siempre hay que definir todas las funciones virtuales de una clase abstracta en sus clases derivadas, no hacerlo así implica que la nueva clase derivada será también abstracta

108

Page 108: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Clases abstractas

Ejemplo:

109

class Persona { public:

Persona(char *n) { strcpy(nombre, n); } virtual void Mostrar() = 0;

protected: char nombre[30];

}; class Empleado : public Persona { public:

Empleado(char *n, int s) : Persona(n), salario(s) {} void Mostrar() { cout << "Empleado: " << nombre << ", Salario: " << salario << endl; }

protected: int salario;

}; Persona *Jose = new Persona(“Jose”); // ERROR Persona *Pepito = new Empleado(“Pepito", 1000);

Page 109: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Interfaces

Las interfaces surgen como una evolución de la POO Programación orientada a componentes

ante la necesidad de reutilizar y agrupar las distintas funcionalidades de un objeto en subconjuntos mas manejables

Definen un cierto comportamiento o cualidades

En términos de C++ es una clase abstracta con métodos virtuales puros

La derivación múltiple nos permitirá luego agrupar varias de esas funcionalidades dentro de una clase nuestro objeto ira cobrando forma a partir de la herencia de

distintas interfaces o cualidades

110

Page 110: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Interfaces

Ejemplo:

111

/* Interface para objetos dibujables */ class IDrawable { public:

Virtual bool IsVisible()=0; virtual void Draw()=0;

}; /* Interface para objetos actualizables */ class IUpdateable { public:

virtual void Update(float dt)=0; }; Class Actor : public IUpdateable, public IDrawable { Public:

bool IsVisible() { return true } void Draw() { ... } void Update (float dt) { ... }

}

Page 111: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Derivación múltiple

C++ permite crear clases derivadas a partir de varias clases base Los objetos heredarán los datos y funciones de todas las

clases base Al construir el nuevo objeto, si es necesario debemos

llamar a los constructores de todas las clases base

112

Page 112: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Derivación múltiple

Ejemplo:

113

class ClaseA { public:

ClaseA(int va = 10) : valorA(va) {} int LeerValor() const { return valorA; }

protected: int valorA;

}; class ClaseB { Public:

ClaseB(int vb = 20) : valorB(vb) {} int LeerValor() const { return valorB; }

protected: int valorB;

}; class ClaseC : public ClaseA, public ClaseB { public:

ClaseC(int va, int vb) : ClaseA(va), ClaseB(vb) {}; int LeerValorA() const { return ClaseA::LeerValor(); } int LeerValorB() const { return ClaseB::LeerValor(); }

};

Page 113: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Derivación múltiple

Problema: Supongamos que tenemos una estructura de clases

La ClaseD heredará dos veces los datos y funciones de la ClaseA, con la consiguiente ambigüedad a la hora de acceder a datos o funciones heredadas de ClaseA

114

Page 114: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Derivación múltiple

Para solucionar esto se usan las clases virtuales

Desde el punto de vista de la ClaseB o ClaseC, no hay

ninguna diferencia entre ésta declaración y la que hemos usado hasta ahora

115

class ClaseB : virtual public ClaseA {}; class ClaseC : virtual public ClaseA {}; class ClaseD : public ClaseB, public ClaseC {};

Sin embargo, ahora la ClaseD sólo heredará una vez la ClaseA

Page 115: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Example 08 –Shapes

Jugando con la herencia y polimorfismo

116

Page 116: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Plantillas

117

class TablaInt { public:

TablaInt(int nElem); ~TablaInt(); int& operator[](int indice) { return pInt[indice]; } ...

private: int *pInt; int nElementos;

}; // Definición: TablaInt::TablaInt(int nElem) : nElementos(nElem) {

pInt = new int[nElementos]; } TablaInt::~TablaInt() {

delete[] pInt; }

Page 117: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Plantillas

Según va aumentando la complejidad de nuestros programas descubrimos que tenemos que repetir una y otra vez las mismas estructuras A menudo tendremos que implementar arrays dinámicos

para diferentes tipos de objetos, o listas dinámicas, pilas, colas, árboles, etc.

El código es similar siempre, pero estamos obligados a rescribir ciertas funciones que dependen del tipo o de la clase del objeto que se almacena

Las plantillas (templates) nos permiten parametrizar estas clases para adaptarlas a cualquier tipo de dato

118

Page 118: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Plantillas

Ejemplo: plantillas de clases

119

template <class T> class Tabla { public:

Tabla(int nElem); ~Tabla(); T& operator[](int indice) { return pT[indice]; }

private: T *pT; int nElementos;

}; // Definición: template <class T> Tabla<T>::Tabla(int nElem) : nElementos(nElem) {

pT = new T[nElementos]; } template <class T> Tabla<T>::~Tabla() {

delete[] pT; }

Page 119: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Plantillas

Ya sólo nos queda saber cómo declarar tablas del tipo que queramos

120

Tabla<int> tablaInt(32); // Tabla de 32 enteros Tabla<float> tablaFloat(12); // Tabla de 12 floats Tabla<bool> tablaBool(10); // Tabla de 10 bools

Page 120: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Plantillas

Ejemplo: plantillas de funciones

De esta forma tendremos definida la función max para

cualquier tipo de dato que tenga implementado correctamente el operador “mayor que”

121

template <class T> T max(T x, T y) {

return (x > y) ? x : y; };

Page 121: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Plantillas

Es posible crear funciones que admitan parámetros que sean una plantilla

Hay dos modos de pasar las plantillas: se puede pasar una instancia determinada de la plantilla la plantilla genérica

122

Page 122: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Plantillas

Ejemplo: paso de una instancia determinada

123

void Incrementa(Tabla<int> &t); ... void Incrementa(Tabla<int> &t) {

for(int i = 0; i < t.NElementos(); i++) t[i]++;

} Tabla<int> TablaInt(5); Tabla<char> TablaChar(20); Incrementa(TablaInt); Incrementa(TablaChar); // ERROR

Page 123: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Plantillas

Ejemplo: paso de la plantilla genérica

124

template<class T> void Mostrar(Tabla<T> &t); ... template<class T> void Mostrar(Tabla<T> &t) { // (4) for(int i = 0; i < t.NElementos(); i++) cout << t[i] << endl; } Tabla<int> TablaInt(5); Tabla<char> TablaChar(20); Mostrar(TablaInt); Mostrar(TablaCadena);

Page 124: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Plantillas

Amigos de plantillas

125

template <class T> class Tabla {

... friend void Mostrar<>(Tabla<T>&); ...

};

template<class T> class Tabla {

... friend void Mostrar<>(Tabla<int>&); ...

};

Page 125: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

El ANSI de C++ define ciertas librerías de plantillas conocidas como STL (Standard Template Library)

Contiene muchas definiciones de plantillas para crear contenedores como listas, colas, pilas, árboles, tablas HASH, mapas, etc.

Además proporciona algoritmos que permiten manipular fácilmente estos contenedores

La STL introduce igualmente el concepto de iterador que permite recorrer fácilmente un contenedor sin tener en cuenta la manera en que ha sido implementado

126

Librería estándar de C++

Page 126: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Example 09 - Plantilla de una pila

127

Page 127: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

C++ proporciona un mecanismo más potente para detectar errores de ejecución: las excepciones

Si uno de esos errores se produce y no implementamos el manejo de excepciones, el programa sencillamente terminará abruptamente

Para ello disponemos de tres palabras reservadas extra: try, catch y throw

128

Page 128: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

Ejemplo: manejo de excepciones

129

#include <iostream> using namespace std; int main() {

int *x; int y = 100000000; try {

x = new int[y]; x[0] = 10; cout << "Puntero: " << (void *) x << endl; delete[] x;

} catch(std::bad_alloc&) {

cout << "Memoria insuficiente" << endl; } cin.get(); return 0;

}

Page 129: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

Manejo de excepciones La manipulación de excepciones consiste en transferir la

ejecución del programa desde el punto donde se produce la excepción a un manipulador que coincida con el motivo de la excepción

Un manipulador consiste en un bloque "try", donde se incluye el código que puede producir la excepción

A continuación encontraremos uno o varios bloques "catch", y entre paréntesis una referencia o un objeto. Estos bloques contienen el código necesario para tratar una excepción de un tipo concreto En el caso del operador "new", si se produce una excepción,

se hace un "throw" de un objeto de la clase "std::bad_alloc"

130

Page 130: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

Captura de excepciones Una excepción se puede producir por un "throw" que se

encuentre dentro del bloque "try" asociado, o en una de las funciones llamadas desde él

Cuando se produce una excepción se busca un manipulador apropiado en el rango del "try" actual

Si no se encuentra se retrocede al anterior, de modo recursivo, hasta encontrarlo

Cuando se encuentra se destruyen todos los objetos locales en todos los niveles por los que hemos pasado

131

Page 131: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

Ejemplo: propagación de excepciones

132

int main() { try {

try { try {

throw 'x'; // valor de tipo char } catch(int i) {} catch(float k) {}

} catch(unsigned int x) {}

} catch(char c) {

cout << "El valor de c es: " << c << endl; } cin.get(); return 0;

}

Page 132: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

Si no se encontrase ningún "catch" adecuado, se abandona el programa, del mismo modo que si se produce una excepción y no hemos hecho ningún tipo de manipulación de excepciones

Para evitar eso existe un "catch" general, que captura cualquier "throw" para el que no exista un "catch"

133

catch(...) { cout << "Excepción imprevista" << endl;

}

Page 133: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

La clase exception Existe una clase base "exception" de la que podemos

heredar nuestras propias clases derivadas para pasar objetos a los manipuladores

Aplicando polimorfismo necesitamos un único "catch" para procesar todas las posibles excepciones

134

class exception { public:

exception() throw() { } virtual ~exception() throw(); virtual const char* what() const throw();

};

Page 134: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

Ejemplo: custom exception

135

class customException : public exception { public:

customException(int mot) : exception(), motivo(mot) {} const char* what() const throw();

private: int motivo;

}; const char* customException::what() const throw() {

switch(motivo) { case 1:

return "Fichero de origen no existe"; case 2:

return "No es posible abrir el fichero de salida"; } return "Error inesperado";

}

Page 135: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

Orden en la captura de excepciones Cuando se derivan clases desde la clase base "exception"

hay que tener cuidado en el orden en que las capturamos Debido que se aplica polimorfismo, cualquier objeto de la

jerarquía se ajustará al catch que tenga por argumento un objeto o referencia de la clase base

136

Page 136: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

Ejemplo: orden en captura excepciones

137

class Excep2 : public exception {} class Excep3 :public Excep2 {} ... try { // Nuestro código } catch(Excep2&) { // tratamiento } catch(Excep3&) { // tratamiento } catch(exception&) { // tratamiento } catch(...) { // tratamiento }

Page 137: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

Especificaciones de excepciones Se puede añadir una especificación de las posibles

excepciones que puede producir una función De este modo indicamos que la función sólo puede hacer

un "throw" de uno de los tipos especificados en la lista El compilador no verifica si realmente es así, sólo se

verifica durante la ejecución, de modo que si se produce una excepción no permitida, el programa termina

138

int Compara(int, int) throw(); int CrearArray(int) throw(std::bad_alloc); int MiFuncion(char *) throw(std::bad_alloc, ExDivCero);

Page 138: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

Excepciones en destructores Está desaconsejado que los destructores puedan producir

excepciones Los destructores pueden ser invocados automáticamente

cuando se procesa una excepción, y si durante ese proceso se produce de nuevo una excepción, el programa terminará inmediatamente

La mejor solución es procesar las excepciones dentro del destructor si es necesario

139

Page 139: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

Ejemplo: excepciones en destructores

140

Miclase::~MiClase() throw () { try { // Necesitamos copiar un fichero cuando se // destruya un objeto de esta clase, pero // CopiaFichero puede generar una excepción

CopiaFichero("actual.log", "viejo.log"); } catch(CopiaEx&) {

cout << "No se pudo copiar el fichero 'actual.log‘” << endl;

} }

Page 140: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

Relanzar una excepción Podemos lanzar una excepción a través de los siguientes

niveles, aunque la hayamos capturado A eso se le llama relanzarla, y para ello se usa "throw;", sin

argumentos

141

Page 141: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Excepciones

Ejemplo: relanzar una excepción

142

try { // Programa Programa();

} catch(int x) {

cout << "Excepción relanzada capturada." << endl; cout << "error: " << x << endl;

} void Programa() {

try { // Operaciones... throw 10;

} catch(int x) {

// Relanzar, no nos interesa manejar aquí throw;

} }

Page 142: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Operadores de cambio de tipo en C++

143

Page 143: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Castings en C++

Hasta ahora hemos usado sólo el casting que existe en C, pero su uso está desaconsejado

Se recomienda usar uno de los nuevos operadores de C++ diseñados para realizar esta tarea

C++ dispone de cuatro operadores para realizar castings: Operador static_cast<> Operador const_cast<> Operador reinterpret_cast<> Operador dynamic_cast<>

144

Page 144: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Castings en C++

Operador static_cast<> Este operador se usa para realizar conversiones de tipo

que de otro modo haría el compilador automáticamente por ejemplo, convertir un puntero a un objeto de una clase

derivada a un puntero a una clase base pública Otro ejemplo, en lugar de usar el operador de conversión

de forma implícita, podemos usarlo mediante el operador static_cast

Este operador se usa con objeto de aclarar el código

145

pBase = static_cast<Base *> (pDerivada); Tiempo Ahora(12,24); int minutos = static_cast<int> (Ahora);

Page 145: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Castings en C++

Operador const_cast<> Se usa para eliminar o añadir los modificadores const y

volatile de una expresión La conversión tiene que ser del mismo tipo, salvo por los

modificadores const o volatile que tengan que aparecer o desaparecer

146

const int x = 10; int *x_var; x_var = const_cast<int*> (&x); // Válido // x_var = &x; // Ilegal, el compilador da error *x_var = 14; // Indefinido

Page 146: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Castings en C++

Operador reinterpret_cast<> Se usa para hacer cambios de tipo a nivel de bits, es decir,

el valor de la expresión a convertir se interpreta como si fuese un objeto del tipo deseado

Este tipo de conversión es peligrosa

147

struct tipoRegistro { char nombre[32]; int edad; float altura;

}; ifstream fentrada("prueba.dat", ios::in | ios::binary); fentrada.read(reinterpret_cast<char *> &pepe2, sizeof(tipoRegistro)); fentrada.close();

Page 147: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Castings en C++

Operador dynamic_cast<> Este operador sólo puede usarse con objetos polimórficos,

cualquier intento de aplicarlo a objetos de tipos fundamentales o agregados o de clases no polimórficas dará como resultado un error

Lo que el programa intentará hacer, durante la ejecución, es obtener un puntero o una referencia a un objeto de cierta una base en forma de clase derivada pero puede que se consiga, o puede que no

148

Page 148: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Castings en C++

Operador dynamic_cast<> Con punteros:

149

void VerSueldo(Persona *p) { if(Empleado *pEmp = dynamic_cast<Empleado *> (p))

pEmp->VerSueldo(); else

cout << "No tiene salario." << endl; }

Page 149: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Castings en C++

Operador dynamic_cast<> Con referencias:

Al aplicar el operador con referencias hay que tener más cuidado, ¿Qué pasará si el casting falla?

150

void VerSueldo(Persona &p) { Empleado& rEmp = dynamic_cast<Empleado &> p; ...

}

Page 150: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ficheros en C++

151

Page 151: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ficheros en C++

Usar streams facilita mucho el acceso a ficheros en disco

veremos que una vez que creemos un stream para un fichero, podremos trabajar con él igual que lo hacemos con cin o cout

Mediante las clases ofstream, ifstream y fstream tendremos acceso a gran cantidad de funciones que nos van a facilitar la tarea

152

Page 152: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ficheros en C++

153

#include <iostream> #include <fstream> using namespace std; int main() {

char cadena[128]; // Crea un fichero de salida ofstream fs("nombre.txt"); fs << "Hola, mundo" << endl; fs.close(); // Abre un fichero de entrada ifstream fe("nombre.txt"); // Leeremos mediante getline, si lo hiciéramos mediante el operador >> sólo leeríamos parte de la cadena: fe.getline(cadena, 128); cout << cadena << endl; return 0;

}

Page 153: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ficheros en C++

Muchos sistemas operativos distinguen entre ficheros de texto y ficheros binarios En general, usaremos ficheros de texto para almacenar

información que pueda o deba ser manipulada con un editor de texto

Ficheros binarios para todo lo demás Un fichero binario permite almacenar estructuras completas,

en las que se mezclen datos de cadenas con datos numéricos

154

Page 154: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ficheros en C++

155

struct tipoRegistro { char nombre[32]; int edad; float altura; }; int main() {

tipoRegistro pepe, pepe2; ofstream fsalida("prueba.dat", ios::out | ios::binary); fsalida.write(reinterpret_cast<char *> &pepe, sizeof(tipoRegistro)); fsalida.close(); ifstream fentrada("prueba.dat", ios::in | ios::binary); fentrada.read(reinterpret_cast<char *> &pepe2, sizeof(tipoRegistro)); fentrada.close(); return 0;

}

Page 155: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ficheros en C++

Ficheros de acceso aleatorio Otra característica importante de los ficheros es la

posibilidad de trabajar con ellos haciendo acceso aleatorio, es decir, poder hacer lecturas o escrituras en cualquier punto del fichero

Para eso disponemos de las funciones seekp y seekg, que permiten cambiar la posición del fichero en la que se hará la siguiente escritura o lectura

156

Page 156: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ficheros en C++

157

char cad[20]; char mes[][20] = {"Enero", "Febrero", "Marzo", ...}; // Acceso aleatorio for(i = 11; i >= 0; i--) {

fentrada.seekg(20 * i, ios::beg); fentrada.read(cad, 20); cout << cad << endl;

} /* Calcular el número de elementos almacenados en un fichero: */ // ir al final del fichero fentrada.seekg(0, ios::end); // leer la posición actual pos = fentrada.tellg(); // El número de registros es el tamaño en bytes dividido entre el tamaño del registro cout << “Número de registros: " << pos/20 << endl;

Page 157: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ficheros en C++

Sobrecarga de operadores << y >> Una de las principales ventajas de trabajar con streams es

que nos permiten sobrecargar los operadores << y >> para realizar salidas y entradas de nuestros propios tipos de datos

158

ostream& operator<<(ostream &os, Registro& reg) { os << "Nombre: " << reg.LeeNombre() <<"\nEdad: " << reg.LeeEdad() << "\nTelefono: " << reg.LeeTelefono(); return os;

}

Page 158: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Ficheros en C++

Example 10 - Importación de modelos 3D

Lectura de ficheros de texto mediante streams

159

Page 159: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Libros recomendados

160

Page 160: Curso 0: Programación orientada a objetos (POO)

P R O G R A M A C I Ó N

ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA

Curso 0: Programación orientada a objetos (POO)

Iván Alduán ([email protected])

(despacho 143 Departamental II, Campus Móstoles)

161