Programación I :: Prof. Yeniffer Peña Conceptos Avanzados de Programación Presentación.

Slides:



Advertisements
Presentaciones similares
Arreglos Unidimensionales y Bidimensionales ESTRUCTURAS DE DATOS I
Advertisements

Curso de java básico (scjp)
Lenguaje de programación Java
Unidad 5 Listas Enlazadas Bibliografía: Algoritmos y Estructuras de datos de Aguilar y Martinez. Unidad 9 Autor: Ing Rolando Simon Titiosky.
Programación I Teoría III
Direcciones, Arreglos y Argumentos de Funciones
Funciones. Programación, Algoritmos y Estructuras de Datos.
Tipos de Datos Básicos y Estructurados
POO en C++: Sintaxis En el .h debe aparecer la declaración de la clase: class NombreClase { private: // atributos y métodos privados public: // atributos.
INFORMATICA I Arreglos 1 CLASE 17.
Informática II Prof. Dr. Gustavo Patiño MJ
Informática II Prof. Dr. Gustavo Patiño MJ
Tema 1. Introducción a la programación (Lenguaje java).
Funcionamiento, programación
Ismael Camarero1. 2 ¿Qué es un PUNTERO?: Un puntero es un objeto que apunta a otro objeto. Es decir, una variable cuyo valor es la dirección de memoria.
Implementación de Listas
Unidad 3 Punteros.
Herramientas para el acceso directo a memoria en C++
¿Qué es un PUNTERO?: Un puntero es un objeto que apunta a otro objeto. Es decir, una variable cuyo valor es la dirección de memoria de otra variable. No.
Vectores en java.
Tema 7: Polimorfismo Antonio J. Sierra. Índice Introducción. Sobrecarga de métodos. Objetos como parámetros. Paso de argumentos. Devolución de objetos.
CI TEORIA semana 8 Subprogramas o funciones Definición de funciones.

Programación Orientada a Objetos usando C++
Métodos Algoritmos y Desarrollo de Programas I. Cuando utilizar métodos  Los métodos se utilizan para romper un problema en pedazos de forma que este.
Material de apoyo Unidad 2 Estructura de datos
Lic. Rosemary Torrico Bascopé
Java Orientado a Objetos CLASES,OBJETOS Y MÉTODOS
Clases y objetos La unidad fundamental de programación OO son las clases. Conjunto de métodos y semántica Qué se va a hacer POO Clase: que define la implementación.
Tema 6: Clases Antonio J. Sierra.
Semana 5 Subprogramas..
Clase 10: Estructuras de datos y arreglos.
Programación Orientada a Objetos usando CONSTRUCTORES DESTRUCTORES.
METODOLOGÍA DE LA PROGRAMACIÓN
PUNTEROS Ing Anghello Quintero.
Asignación de Espacio No Contiguo
Informática Ingeniería en Electrónica y Automática Industrial
Aplicación de estructuras de datos
1 Asignación Dinámica de Memoria Agustín J. González Versión original de Kip Irvine ELO 329.
Herramientas de polimorfismo y herencia en C++
Manejo de Punteros y objetos en memoria dinámica en C++
Unidad II Introducción a la programación en C++
FUNCIONES Conceptos básicos. Retorno de una función Clases de funciones. Paso de parámetros. Funciones y arrays.
APRENDIZ: SANDRA L. CAICEDO C. ORDEN: 20194
Informática Ingeniería en Electrónica y Automática Industrial
Programación en C para electrónicos
Elementos básicos del lenguaje
PUNTEROS Y REFERENCIAS
APUNTADORES.
Clases y Objetos en Java ELO329: Diseño y Programación Orientados a Objetos.
Programación Orientada a Objetos
Punteros Recomendado: 1. Nivelación Funciones
1 Asignación Dinámica de Memoria Agustín J. González ELO 329.
Capitulo 4 Arreglos o Arrays Unidimensionales Bidimensionales Strings
PRINCIPIOS DE PROGRAMACIÓN

Fundamentos de Programación
6. Clases y Métodos..  6.1 Structs  6.2 Funciones  6.3 Namespaces  6.4 Clases.
 Las funciones son un conjunto de instrucciones que realizan una tarea específica. En general toman unos valores de entrada, llamados parámetros y proporcionan.
MEMORIA DINÁMICA.
PUNTEROS. Los punteros son de amplia utilización en programación y muchos lenguajes permiten la manipulación directa o indirecta de los mismos. Su razón.
Tema 1. Estructuras de datos Objetivo: Objetivo: El alumno resolverá problemas de almacenamiento, recuperación y ordenamiento de datos y las técnicas de.
Prof. Manuel B. Sánchez. Declaración de Objetos Una vez que la clase ha sido implementada se pueden declarar objetos como variables locales de métodos.
Métodos en Java. Estructura de un programa en Java ► La relación con la vida misma la podemos ver en el siguiente comentario: Imaginemos que dos clases.
PROF. RAFAEL MONTENEGRO B. UNELLEZ-APURE Introducci Ó n a los Arreglos (“arrays”) en C++
UNIVERSIDAD TECNOLÓGICA DE PANAMÁ Facultad de Ingeniería de Sistemas Computacionales Programa de Lic. en Informática Educativa Computación.
Lenguaje de Programación II Prof. Rafael Montenegro B. Carrera: T.S.U en Informática Periodo: 2014-I.
Computación I :: Prof. Yeniffer Peña Lenguaje C Presentación Computación I.
Computación I :: Prof. Yeniffer Peña Lenguaje C Presentación Computación I.
Uso de punteros Unidad III – Conceptos Avanzados de Programación Programación I
Transcripción de la presentación:

Programación I :: Prof. Yeniffer Peña Conceptos Avanzados de Programación Presentación

Programación I Tipos de Herencia Si la herencia es public, la clase hija podrá usar los atributos y métodos de la sección pública de la clase padre en forma pública, es decir desde el main. Podrá usar la sección protegida pero desde dentro de sus métodos. class CajaColor : public Caja { }; Si la herencia es protected, la clase hija podrá usar los atributos y métodos de la sección pública y protegida de la clase padre pero desde dentro de sus métodos. Haciéndolos dentro de ella protegidos. No tendrá acceso desde el main. class CajaColor : protected Caja { }; Programación I

Tipos de Herencia Si la herencia es private, la clase hija podrá usar los atributos y métodos de la sección pública y protegida de la clase padre pero desde dentro de sus métodos. Haciéndolos dentro de ella privados. No tendrá acceso desde el main. class CajaColor : private Caja { }; Si no se coloca el tipo de herencia se asume protegida class CajaColor : Caja { }; La sección privada de una clase padre es no accesible desde una clase hija. Programación I

Tipo de Herencia: Public #include “iostream.h” #include “conio.h” class Animal { protected: char raza[20]; void asignarRaza(char *r){ strcpy(raza,r); cout<<"Raza: "<<raza<<endl; } public: Animal(){ } int mostrar() {cout<<“Mostrar de Animal”<<endl; } }; class Mamifero: public Animal { public: Mamifero():Animal(){ } int alimentar() {cout<<“Alimentar a Mamifero”<<endl; } }; Programación I Herencia Pública void main(){ Mamifero obj; obj.alimentar(); obj.mostrar(); obj.asignarRaza(); //Error… cin.get(); }

Programación I Tipo de Herencia: Public #include “iostream.h” #include “conio.h” class Animal { protected: char raza[20]; void asignarRaza(char *r){ strcpy(raza,r); cout<<"Raza: "<<raza<<endl; } public: Animal(){ } int mostrar() {cout<<“Mostrar de Animal”<<endl;} }; class Mamifero: public Animal { public: Mamifero():Animal(){ } int alimentar() {cout<<“Alimentar a Mamifero”<<endl; this->asignarRaza(“Collie”); } }; Programación I Herencia Pública void main(){ Mamifero obj; obj.alimentar(); obj.mostrar(); obj.asignarRaza(); //Error… cin.get(); }

Programación I Tipo de Herencia: Protected #include “iostream.h” #include “conio.h” class Animal { protected: char raza[20]; void asignarRaza(char *r){ strcpy(raza,r); cout<<"Raza: "<<raza<<endl; } public: Animal(){ } int mostrar() {cout<<“Mostrar de Animal”<<endl; } }; class Mamifero: protected Animal { public: Mamifero():Animal(){ } int alimentar() {cout<<“Alimentar a Mamifero”<<endl; } }; Programación I Herencia Protegida void main(){ Mamifero obj; obj.alimentar(); obj.mostrar(); //Error… obj.asignarRaza(); //Error… cin.get(); }

Programación I Tipo de Herencia: Protected #include “iostream.h” #include “conio.h” class Animal { protected: char raza[20]; void asignarRaza(char *r){ strcpy(raza,r); cout<<"Raza: "<<raza<<endl; } public: Animal(){ } int mostrar() {cout<<“Mostrar de Animal”<<endl;} }; class Mamifero: protected Animal { public: Mamifero():Animal(){ } int alimentar() {cout<<“Alimentar a Mamifero”<<endl; this->asignarRaza(“Collie”); this->mostrar(); } }; Programación I Herencia Protegida void main(){ Mamifero obj; obj.alimentar(); obj.mostrar(); //Error… obj.asignarRaza(); //Error… cin.get(); }

Programación I Un ejemplo recientemente utilizado es con los operadores >> y <<, que además de ser usados por C++ para desplazamiento de bits también permiten realizar operaciones de E/S por consola. Esto es posible porque en la librería iostream.h, estos operadores son sobrecargados. Los operadores sobrecargados toman un significado adicional para la clase con la que está directamente relacionada y además, sigue teniendo todos sus significados anteriores. Sobrecarga de Operadores

Programación I La sobrecarga de operadores es el proceso de cambiar el significado de un operador para su uso con objetos de una clase específica. Cuando se sobrecarga un operador, se específica una función que C++ invoca cada vez que la clase utiliza el operador sobrecargado. Los operadores se pueden sobrecargar escribiendo una definición de función (con encabezado y cuerpo), excepto que ahora el nombre de la función es la palabra reservada operator, seguida del símbolo del operador que se desea sobrecargar. Sobrecarga de Operadores

Programación I Por ejemplo, imagine que tenemos dos objetos de una clase trabajador y queremos sumarlos. trabajador obj1, obj2; obj1+ obj2 Para poder realizar la operación anterior, tendríamos que sobrecargar el operador + porque éste solo suma numeros y objetos de la clase String. Veamos el siguiente ejemplo: Sobrecarga de Operadores

Programación I #include “iostream.h” #include “conio.h” #include “string.h” class trabajador{ char nombre[40]; int edad; float sueldo; public: //Constructores trabajador(); trabajador(char * n, int e, float s); //Función que sobrecarga el operador + trabajador operator+ (trabajador obj); //Otras funciones miembro void mostrar(); }; Sobrecarga de Operadores

Programación I trabajador::trabajador(){ } trabajador::trabajador(char * n, int e, float s){ strcpy(nombre,n); edad=e; sueldo=s; } trabajador trabajador::operator+ (trabajador obj){ trabajador obj_aux; sueldo obj_aux.sueldo = sueldo + obj.sueldo; edad obj_aux.edad = edad + obj.edad; nombre strcpy(obj_aux.nombre, strcat(nombre, obj.nombre)); return obj_aux; } void trabajador::mostrar(){ cout<<“\nNombre: ”<<nombre; cout<<“\nEdad: ”<<edad; cout<<“\nSueldo: ”<<sueldo; } Sobrecarga de Operadores sueldoedadnombre sueldo, edad y nombre son los atributos del objeto que invoca

Programación I void main(){ trabajador obj1(“Luis”, 36, 700); trabajador obj2(“Ana”, 30, 900); + obj1 = obj1 + obj2; obj1.mostrar(); getch(); } Sobrecarga de Operadores Nombre: LuisAna Edad: 66 Sueldo: 1600 Objeto que invoca Objeto que Se envía como argumento

Programación I Punteros, Operadores, Inicialización. Relación entre punteros y arreglos. Relación entre punteros y funciones. Utilización de memoria dinámica para manejar arreglos mediante el uso de punteros. Punteros a objetos. Vectores dinámicos de objetos. Uso de objetos dinámicos Atributos dinámicos. Creación de objetos con atributos dinámicos. Destrucción de objetos con atributos dinámicos. Operador de asignación para objetos con atributos dinámicos. Unidad III. Conceptos Avanzados de Programación PUNTEROS

Programación I Zona de memoria que contiene la dirección de otra zona de memoria. Un apuntador contiene la dirección de memoria de una variable que contiene un valor específico. En este sentido, un nombre de variable se refiere directamente a un valor y un apuntador se refiere indirectamente a un valor. Todas las variables tienen una ubicación en la memoria y en esa ubicación se almacena su valor Punteros

Programación I Todas las variables tienen una ubicación en la memoria y en esa ubicación se almacena su valor. Por ejemplo si se tiene la instrucción: int x = 200; La dirección de x es AF13 y su valor 200 es guardado en esa dirección. Las direcciones de memoria son notadas con el sistema hexadecimal Punteros x 200 Memoria AF13

Programación I Proporciona medios por los cuales se pueden modificar los argumentos de llamada de las funciones. Esto es, simular llamadas por referencia. Se usan para soportar rutinas de asignación dinámica de C. Crear y manipular estructura de datos que puedan crecer o encogerse caso de estas listas enlazadas, colas, pilas y árboles. Pueden mejorar la eficiencia de ciertas rutinas. Punteros Ventajas:

Programación I Puede provocar fallo del sistema por no estar inicializados o mal uso (forma incorrecta) de los mismos. Punteros Desventajas: Formato: Pueden ser de cualquier tipo de datos. Hay punteros que contienen la dirección de variables de cualquier tipo. tipo_dato * Nombre_Variable; Indicador de puntero

Programación I & Se refiere a su dirección. * Indica el valor de la variable puntero. Punteros Operadores: int i, *ap, variable; i ap variable Memoria ABF0 ABF4 ABF8 150 variable=150; ap = &variable; i = *ap; ABF8150 Ejemplo:

Programación I Si se usa un puntero antes de darle valor probablemente falle el programa y el sistema operativo, por eso es tan importante la inicialización de ellos. Se puede hacer de dos formas: la primera es asignando la dirección de una variable y la segunda es inicializarlo en el valor nulo. Ejemplo: Punteros Inicialización de Punteros: void main ( ) { int variable, *Ap1, *Ap2, *Ap3; Ap1=&variable; //Su contenido depende de la //dirección de variable Ap2=NULL; Ap3=0; }

Programación I void main ( ) { char k, *p; k=’m’; *p=k; } p=&k; Punteros Errores Comunes: void main ( ) { int n, *p; n=10; p=n; printf(“%d”,*p); } p=&n; Puntero no inicializado Error en el uso del Puntero

Programación I Aunque & y * representa AND a nivel de bits y multiplicación cuando se usan como operadores punteros tienen mayor prioridad que todos los operadores aritméticos. Las variables punteros deben apuntar al tipo de dato correcto porque pueden dar resultados no deseados. El operador & y * son complementos, cuando se operan ambos de manera consecutiva en el apuntador, en cualquier orden, se imprimirá el mismo resultado. El especificador de conversión %p extrae la localización de memoria de un apuntador en formato hexadecimal. Punteros Notas Importantes:

Programación I void main( ) {int n, *p; n=5; p=&n printf(“%d”,n); printf(“\n%p”,p); printf (“\n%d”,*p); } Punteros Ejemplo: n p Memoria AC01 AD12 AC015 Pantalla 5 AC01 5

Programación I Punteros Manipulación de Punteros: Ejemplo: void main ( ) { int n = 5; int *np = &n; printf(“n = %d y *np = %d”, n, *np); *np++; printf(“n = %d y *np = %d”, n, *np); *np = *np + 20; printf(“n = %d y *np = %d”, n, *np); } n np Memoria AC01 AD12 AC

Programación I Punteros Manipulación de Punteros: Ejemplo: void main ( ) { int n = 5; int *np = &n; printf(“n = %d y *np = %d”, n, *np); *np++; printf(“n = %d y *np = %d”, n, *np); *np = *np + 20; printf(“n = %d y *np = %d”, n, *np); } n np Memoria AC01 AD12 AC

Programación I Las operaciones se realizan a nivel de tipo de elementos y los operadores usando son +, -, ++,--. Punteros Aritmética de Punteros: Ejemplo: void main ( ) { char var1 = ‘a’; char *caracter = &var1; int var2 = 5; int *entero = &var2;... caracter --; entero++;... } 0600 Z 0601 var a var caracter entero caracter entero

Programación I Un arreglo es un puntero a la dirección de su primer elemento. Un nombre de arreglo sin índice devuelve la dirección de comienzo del arreglo que es el primer elemento. Se puede entonces intercambiar información entre punteros y arreglos del mismo tipo. Punteros Relación entre Punteros y Arreglos:

Programación I Para acceder al tercer elemento de cadena se puede hacer de 2 formas: Punteros Relación entre Punteros y Arreglos: char cadena[ ]=“Unet”; char *Ap; Ap= cadena; //Ap tiene la dirección del //primer elemento de la cadena AC01 AC02 AC03 AC04 AC05 cadena Un e t \0 DF78 Ap AC01 cadena[2] //Tradicional: Ordenación de arreglos ó *(Ap+2) //Usando aritmética de punteros. //Acceso más rápido

Programación I En C++ existen dos tipos de parámetros al invocar funciones, estos son: por valor y por referencia. Cuando los argumentos se pasan en llamada por valor, se efectúa una copia del valor del argumento y ésta se pasa a la función invocada. Las modificaciones a la copia no afectan el valor original de la variable. La llamada de funciones donde intervienen parámetros por punteros se le llama pase por referencia y debe ser utilizada sólo en llamadas confiables, porque las modificaciones de estas variables se mantienen y afectan la variable original. Funciones Relación entre Punteros y Funciones

Programación I Cuando un argumento se pasa por referencia, la dirección del dato es pasada a la función. El contenido de esta dirección puede ser accedido libremente. Además, cualquier cambio que se realiza al dato (al contenido de la dirección) será reconocido en ambas, la función y rutina de llamada. Así, el uso de punteros como argumentos de funciones permite que el dato sea alterado globalmente desde dentro de la función. Los argumentos formales que sean punteros deben ir precedidos por un asterisco (*). Funciones

Programación I Funciones #include void pase_valor_referencia (int, int *); void main( ) { int X=5, Y=10; printf(“\nEl valor inicial de X es: %d y el de Y es: %d“, X, Y); pase_valor_referencia (X, &Y); printf(“\nEl valor final de X es: %d y el de Y es: %d“, X, Y); getch( ); } void pase_valor_referencia (int x, int *y) { x = x + 2; *y = *y + 2; } Paso de argumentos a una función: Pase por valor y por referencia

Programación I Para pasar todo un arreglo a una función, el nombre del arreglo debe aparecer solo, sin corchetes, ni índices, como un argumento real en la llamada a la función. El correspondiente argumento formal debe ser declarado como un arreglo, si se trata de un vector se escribe con un par de corchetes vacíos. Los arreglos multidimensionales se definen prácticamente de la misma manera que los unidimensionales, excepto que se requiere un par separado de corchetes para cada índice. Pudiéndose dejar el primer par de corchetes vacíos. Si un elemento del arreglo es alterado dentro de una función, esta alteración será reconocida en la parte del programa desde la que se hizo la llamada. Funciones Paso de arreglos a una función:

Programación I Funciones void cargar1 (int nx, int vector[ ]); void cargar2 (int nx, int *vector ); void promedio1(int nx, int vector[ ]); void promedio2(int nx, int *vector); void main( ) { int i; int vec [5]; cargar1(5,vec); promedio1(5,vec); cargar2(5,vec); promedio2(5,vec); getch(); } void cargar1 (int nx, int vector[ ] ) { for (int i=0; i<nx; i++){ printf(“\nIngrese un numero: ”); scanf(“%d”,&vector[i]); } } Paso de arreglos a una función: void cargar2 (int nx, int *vector ) { for (int i=0; i<nx; i++){ printf(“\nIngrese un numero: ”); scanf(“%d”,vector+i); } } void promedio1 (int nx, int vector[ ]) { int acum=0; for (int i=0; i<nx; i++) acum=acum+vector[i]; printf(“\nProm1:%.2f”,(float)acum/nx ); } void promedio2 (int nx, int *vector) { int acum=0; for (int i=0; i<nx; i++) acum=acum+ *(vector+i); printf(“\nProm2:%.2f”,(float)acum/nx ); }

Programación I Funciones void pase_cadenas (char *r, char est[], char * cap, char v_mun[][20]); void main( ) { char resp, estado[20], capital[20], v_municip[5][20]; pase_cadenas (&resp, estado, capital, v_municip); printf(“%c %s %s %s”, resp, estado, capital, v_municip[0]); getch(); } void pase_cadenas (char *r, char est[], char *cap, char v_mun[][20]) { *r = ‘S’; strcpy(est,”Tachira”); strcpy(cap,”San Cristobal”); strcpy(v_mun[0],”Lobatera”); } Pase de cadenas por referencia a una función:

Programación I Se utiliza para abrir memoria a variables dinámicas. Ejemplo: int * x = new int [MAX]; Punteros Punteros y Memoria Dinámica: Operador new x Después de utilizarse este operador, la memoria debe liberarse con el operador delete. Ejemplo: delete vector;

Programación I void recibeVector1(int *, int); void recibeVector2(int [], int); void main (int argc, char * argv[]){ int *vec, tam; printf("Tamanho:"); scanf("%d",&tam); vec = new int [tam]; recibeVector1(vec, tam); recibeVector2(vec,tam); } void recibeVector1(int *v, int t){ for(int i=0; i<t;i++) *(v+i)=i; } void recibeVector2(int v[], int t){ for(int i=0; i<t;i++) v[i]+=i; } Punteros Punteros y Memoria Dinámica: Operador new

Programación I void recibeMatriz(int **, int, int); void main (int argc, char * argv[]){ int **mat, nfil, ncol; printf("Filas:"); scanf("%d",&nfil); printf("Columnas:"); scanf("%d",&ncol); mat = new int * [nfil]; Punteros Punteros y Memoria Dinámica: Operador new mat for(int i=0; i<nfil;i++) mat[i] = new int [ncol]; recibeMatriz(mat, nfil, ncol); } void recibeMatriz(int **m, int f, int c){ for(int i=0; i<f;i++) for(int j=0; j<c; j++) scanf(“%d”, (*(m+i)+j) ); }

Programación I malloc Solicita un bloque de (size) bytes de memoria. Si no hay espacio disponible malloc devuelve null. Prototipo: void * malloc (size_t size); Ejemplo: x = (int *) malloc(MAX * sizeof(int) ); Esta función reserva un bloque de memoria cuyo tamaño (en bytes) es equivalente a MAX=5 cantidades enteras. El puntero x apunta al comienzo del bloque de memoria. La solicitud de bloque de memoria es hasta 64K. Incluir librerías stdlib.h y alloc.h Punteros Punteros y Memoria Dinámica: malloc

Programación I Punteros #include void main() { int *Apunt, n, i; ´ clrscr(); printf(“Cantidad de datos a ingresar: ”); scanf(“%d”,&n); //Para reservar memoria Apunt = ( int * ) malloc ( n * sizeof (int) ); //malloc devuelve un void * printf(“Bytes reservados para cada dato: %d\n”, sizeof(Apunt) ); //Para leer la lista de números en el vector for(i=0; i<n; i++){ printf(“Ingrese Apunt[%d]: ”, i); scanf(“%d”, Apunt + i ); } //En vez de &Apunt[i] //Para mostrar la lista de números del vector for(i=0; i<n; i++) printf(“Apunt[%d]= %d\n”, i, *(Apunt +i) ); // En vez de Apunt[i] //Para liberar la memoria utilizada free(Apunt); getch(); } Punteros y Memoria Dinámica.

Programación I Supongamos que Matriz es un arreglo bidimensional de enteros con 10 filas y 5 columnas. Usando una variable puntero para representar la Matriz, éste se puede declarar: int (*Matriz)[10]; ó int (*Matriz)[5]; En vez de Matriz [10][5]; Luego, se pide memoria para la dimensión que falta por representar: for (i=0; i<10; i++) Matriz[i] = (int *) malloc (5*sizeof(int) ); ó for (i=0; i<5; i++) Matriz[i] = (int *) malloc (10*sizeof(int) ); Punteros Punteros y Memoria Dinámica:

Programación I Punteros #include void leer(int * [5], int, int); void mostrar(int * [5], int, int); void main() { int * Matriz [5], n, i; clrscr(); printf(“Cantidad de datos a ingresar: ”); scanf(“%d”,&n); //Para reservar memoria for (i=0; i<5; i++) Matriz[i] = ( int * ) malloc ( n * sizeof (int) ); //malloc devuelve un void * leer(Matriz, 5, n); mostrar(Matriz, 5, n); free(Matriz); getch(); } Punteros y Memoria Dinámica. void leer(int * m [5], int nfil, int ncol){ int x, y; for (x=0; x<nfil; x++) for (y=0; y<ncol; y++) { printf(“Ingrese Matriz[%d][%d]: ”, x, y); scanf(“%d”, (*(m+x) + y) ); } //ó (m[x] + y) En vez de &m[x][y] } void mostrar(int * m [5], int nfil, int ncol){ int x, y; printf(“\nDatos de la Matriz\n”); for (x=0; x<nfil; x++){ for (y=0; y<ncol; y++) printf(“ %d”, *(*(m+x) + y)); //ó *(m[x] + y) En vez de m[x][y] printf(“\n”); } }

Programación I realloc Ajusta el tamaño de memoria previamente solicitada al nuevo tamaño, trasladando el contenido a una nueva localización de memoria si es necesario. Prototipo: void * realloc (void * block, size_t size); block: Puntero a un bloque de memoria previamente solicitado con instrucción malloc, calloc o realloc. size: El nuevo tamaño en bytes que tendrá el bloque de memoria Punteros Punteros y Memoria Dinámica: realloc

Programación I Punteros Punteros y Memoria Dinámica:

Programación I En C++ se pueden definir punteros a objetos, ya que las clases son tipos, y se pueden declarar punteros de cualquier tipo. Por ejemplo: Por tanto, si se tiene una clase Punto, se puede crear: Funciones Punteros a objetos class Punto { private: int coorx; int coory; public: …… }; int *p1; char *c; Punto * p1; Esta declaración no llama al constructor, ya que se trata de una variable puntero y no de un Punto

Programación I Para trabajar con el puntero, se le puede asignar la dirección de memoria de un objeto de tipo Punto. Funciones Punteros a objetos class Punto { private: int coorx; int coory; public: Punto(int a, int b); int get_x(); int get_y(); void set_x(int a); void set_y(int a); void visualizar(); }; Punto c(2,3); Punto *p1; p1 = & c; p1->visualizar(); (*p1).visualizar(); p1->set_x(8);

Programación I También se pueden usar los operadores de las variables dinámicas: new y delete Funciones Punteros a objetos El operador new sigue los siguientes pasos: 1.Crea espacio para el objeto. 2.Llama al constructor especificado. El operador delete realiza los pasos inversos: 1.Llama al destructor. 2.Libera la memoria ocupada por el objeto.

Programación I También se pueden crear vectores dinámicos de objetos: Funciones Vectores dinámicos de objetos El operador new 1.Crea espacio para los 100 objetos. 2.Llama al constructor por defecto para cada objeto (0 a 99). El operador delete realiza los pasos inversos 1.Llama al destructor para cada punto (99 a 0). 2.Libera la memoria.

Programación I Antes de usar el objeto, pasándole mensajes a través del puntero que lo apunta, se ha de crear el objeto con new. Cuando ya no se necesita el objeto se destruye con delete. Funciones Uso de objetos dinámicos void main () { Punto *p; //Crear p = new Punto(); //Creado el objeto dinámico //Usar p->visualizar(); //Uso del objeto mediante envío de mensaje //Destruir delete p; //Liberar memoria del objeto }

Programación I Se está en presencia de ellos, cuando dentro de una clase se declaran atributos en forma de punteros: Funciones Atributos dinámicos Ambas declaraciones son equivalentes pero con implementación distinta.

Programación I Cuando se crea un objeto con atributos dinámicos, se crean al m ismo tiempo esos atributos. ¿Dónde? En el constructor. Funciones Creación de objetos con atributos dinámicos

Programación I Para cada objeto de la clase Punto que se crea, se crean a su vez sus atributos dinámicos. Funciones Creación de objetos con atributos dinámicos

Programación I ¿Cuál es el efecto de la siguiente declaración?. Funciones Creación de objetos con atributos dinámicos

Programación I De la misma forma. Cuando se destruye un objeto con atributos dinámicos, se destruyen al mismo tiempo esos atributos. ¿Dónde? En el destructor. Funciones Destrucción de objetos con atributos dinámicos Es el que se ejecuta automáticamente cuando se destruyen objetos

Programación I Cuando se copian objetos, se ejecuta el operador de asignación de la clase. Si en la clase no está definido ningún operador de asignación, el compilador realiza una copia bit a bit. Funciones Operador de asignación para atributos dinámicos void main () { Punto p1(2,5), p2; p2 = p1; } El problema está en que ambos objetos comparten memoria Ocurre una pérdida de memoria, porque se copian los atributos igualando los punteros

Programación I En esta situación, 1.¿Qué ocurre cuando se modifica el objeto p1? 2.¿y cuando se destruye el objeto p1? Funciones Operador de asignación para atributos dinámicos

Programación I Esto se resuelve sobrecargando el operador de asignación. Cuando las clases definen atributos dinámicos, el operador de asignación se hace imprescindible. El operador de asignación debe copiar los contenidos de los punteros, no los punteros como tal. Funciones Operador de asignación para atributos dinámicos Como el objeto sobre el que se copia, ya tiene creados los atributos dinámicos, simplemente se copia lo apuntado. Devuelve una referencia de ese objeto

Programación I Funciones La clase Punto completa class Punto { private: int * x; int * y; public: Punto(int a, int b); ~Punto(); Punto& operator = (Punto p); int get_x(); int get_y(); void set_x(int a); void set_y(int a); void visualizar(); }; El archivo Punto.h

Programación I Funciones La clase Punto completa Punto::Punto(int a, int b) { x= new int; y = new int; *x = a; *y = b; } El archivo Punto.cpp Punto::~Punto() { delete x; delete y; } Punto& Punto::operator = (Punto p) { *x = *p.x; *y = *p.y; return *this; } void Punto::set_x(int a) { *x = a; } void Punto::set_y(int a) { *y = a; } int Punto::get_x() { return *x; } int Punto::get_y() { return *y; }

Programación I Punteros Conceptos Avanzados de Programación