You are on page 1of 10

100

APUNTADORES

Una de las fortalezas del lenguaje C es el uso de apuntadores. Un apuntador es una variable cuyo contenido o valor es una direccin de memoria. De esta forma un apuntador entero es una variable que guarda la direccin de una variable entera, un apuntador a carcter es una variable cuyo contenido es la direccin de una variable carcter, y as aplicamos el concepto a cualquier tipo de variable. La representacin simblica de la variable apuntador es una flecha que apunta al contenido de una cajita, la cajita es la variable y la flecha es el apuntador o direccin de esa variable. I

100

Representacin grafica de la variable entera j, cuyo valor es 100 y una variable apuntador i que apunta a la direccin de j.

j=100; i= &j;

Definicin en cdigo C del ejemplo anterior Fig 1

1. int main() 2. { 3. // Zona de Declaracin de Variables del Programa principal 4. int *i, j; 5. j=100; 6. i= &j; 7. *i=j; 8. cout << " El Valor de la direccion de j, &j= i " << i << " " 9. << &j << endl; 10. cout << " El Valor del contenido de j j= *i " << *i << " " << 11. j << endl; 12. system("Pause"); // Hacer una pausa 13. return 0; // Valor de retorno al S.O. 14. }

Prog I

En el programa anterior se observa la declaracin de una variable apuntador i (int *i lnea nm. 4) lo que indica que la variable i es una variable apuntador y cuyo contenido ser la direccin de una variable entera. La lnea 6 se la asigna a i la direccin de j (i= &j; &j hace referencia a la direccin de j) y en la siete se le asigna el contenido de j que en nuestro caso es 100 al contenido de i (*i, *i se refiere al contenido de i). Esta operacin es redundante dado a al asignarse la direccin ya queda establecido el contenido. El programa anterior imprime la direccin y el contenido tanto de j como de i: lneas 8 al 11.

Ejemplo utilizando funciones con parmetro tipo apuntador

1. 2. 3. 4.

#include <iostream> #include <cstdlib> using namespace std; void cuadrado( int* base);

/ 5. int main() 6. { 7. 8. base : 10. 11. 12. 13. 14. 15. el 16. 17. 18. 19. 20. 21. 22. 23. 24. 25. 26. 27. 28. 29. int *n,i,*j; cout <<" Indique el valor de la 9. "<<endl; cin >> i; n=&i; j=n; cuadrado(n); // probar luego directamente con parametro &i asi: cuadrado(&i); cout <<" el valor del parmetro procesado es: "<< *n << endl; cout <<" el contenido de j es:"<< *j << endl;

(lin 13) Se invoca la funcin cuadrado con el parmetro n donde n = &i es decir n es un apuntador que apunta a la misma direccin de i. (lin14) se sugiere el ejercicio de invocar la misma funcin pero directamente con el valor &i. (lin 16) se imprime *n [el contenido del apuntador n] el cual coincide con el contenido de j [*j] ambos apuntadores apuntan a la misma direccin La otra observacin es que el pasaje de parmetro de esta forma es por referencia:
11. 12. 13. n=&i; j=n; cuadrado(n);

system("Pause"); // Hacer una pausa return 0; // Valor de retorno al S.O. } void cuadrado(int* base) { *base *= *base; return; }

Es equivalente a : 12. 13. j=n; cuadrado(&i);

Prog I-a

ESTRUCTURAS Cdigo para declarar en C++ una estructura compuesta de dos elementos simples
1. #include <iostream> 2. #include <stdlib.h> 3. #include <cstdlib> 4. #include <stdio.h> 5. using namespace std; 6. typedef struct lista { 7. int valor; 8. struct lista *sig; 9. }Nodo; 10. 11. typedef Nodo *cc; 12. void Insertar(cc *c, int dato); 13. void Imprimir(cc c); 14. int ListaVacia(cc lista); 15. void MostrarLista(cc lista); 16. int calificacion; 17. void menu(); 18. 19. // la funcin main comienza la 20. 20. ejecucin del programa 21. int main() 22. { 23. cc c; 24. int dato;

Las estructuras son unidades lgicas de memoria definidas por el usuario y conformadas por varios tipos de datos diferentes: En la lnea 23 se declara la variable c de tipo cc donde cc se declara en la lnea 11 como un tipo apuntador a Nodo. Por lo tanto c es una variable tipo apuntador a Nodo. Nodo es la estructura compuesta por una variable entera denominada valor y otra que es un apuntador a un objeto idntico a la estructura definida. Lneas 6 al 10.

Fig 2

OPERACIONES SOBRE ESTRUCTURAS (crear e insertar)

1. void Insertar (cc *c, int dato) 2. { 3. cc tempo; 4. while (dato != -1){ 5. tempo = new Nodo; 6. tempo->valor = dato; 7. tempo->sig = *c; 8. *c = tempo; 9. 10. cout << " Indique el 11. siguiente valor de la lista (-1:fin) " 12. <<endl; 13. cin >> dato; 14. } 15. return;}

La funcin Insertar recibe como parmetro un valor por referencia [ver programa I-a] tipo apuntador a nodo (lin. 1). La funcin dispone tambin de una variable local tipo apuntador a nodo: tempo (lin 3). La funcin new crea una estructura tipo nodo y se la asigna a la variable tempo (A).(lin 5). A tempo.valor se le asigna el valor del parmetro tipo entero: dato y a tempo.siguiente el cual es de tipo apuntador se le asigna el valor del parmetro *c en este punto tanto tempo.siguiente como *c apuntan a la misma estructura(B)(lin7) En (lin8) a *c se le asigna a tempo, en este caso tanto tempo como *c apuntan a la estructura creada previamente.(C)

TEMP O TEMPO VALOR SIG VALOR: DATO *C

SIG:

TEMP O

VALOR: DATO2 SIG:


NULL

B
VALOR DAT SIG *C

VALOR DAT SIG


NUL

Fig 3

LISTAR
1. void MostrarLista(cc lista) 2. { 3. cc nodo = lista; 4. 5. 6. 7. 8. 9. 10. while(nodo) { printf("%d -> ", nodo->valor); nodo = nodo->sig; } printf("\n"); return; }

En este caso el paso de parmetro es por valor. Lista es un parmetro por valor, es decir no se altera su contenido al retornar la funcion. El algoritmo es muy sencillo: Nodo se le asigna el parmetro lista: ambos apuntan ahora a la misma direccin. (lin. 3) Mientras nodo no apunte avaco: (lin 4) Se imprime nodo.valor; (lin 5) Se recorre lea lista : lista = lista.siguiente. IMPORTANTE: el pasaje de parmetro aqu debe ser estrictamente por valor

Fig 4

EL PROGRAMA COMPLETO
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 #include <iostream> #include <stdlib.h> #include <cstdlib> #include <stdio.h> using namespace std; typedef struct Lista { int valor; struct Lista *sig; }Nodo; typedef Nodo *cc; void Insertar(cc *c, int dato); void Imprimir(cc c); int ListaVacia(cc lista); void MostrarLista(cc lista); int calificacion; void menu(); // la funcin main comienza la ejecucin del programa int main() { cc c; int dato; c = NULL; do { menu(); switch ( calificacion ) { // estructura switch anidada en un while case 'A': case 'a': cout << " Indique el valor de la lista (-1:fin) .." <<endl; cin >> dato; Insertar(&c,dato); break; case 'E': case 'e': Imprimir(c); system("pause"); break; case 'f': case 'F': calificacion = EOF; break; case '\n': // ignora nuevas lneas, case '\t': // tabuladores, case ' ': case EOF: // y espacios en la entrada break; case 's': case 'S': // sale de switch calificacion = EOF; break; default: // atrapa todos los dems caracteres cout << "Se introdujo una letra incorrecta." << "Introduzca una nueva letra." << endl; break; // opcional; de cualquier manera sale de switch } // fin de switch

} while (calificacion != EOF);// fin de while system("PAUSE"); return 0; // indica terminacin exitosa } // fin de la funcin main void Insertar(cc *c, int dato) { cc tempo; while (dato != -1){

72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111

tempo = new Nodo; tempo->valor = dato; tempo->sig = *c; *c = tempo; cout << " Indique el siguiente valor de la lista (-1:fin) .." <<endl; cin >> dato; } return; } void Imprimir(cc lista) { cc tempo = lista; if (ListaVacia(lista)) printf("Lista vaca\n"); else while (tempo) { cout << " " << tempo->valor<< endl; tempo = tempo->sig;} cout << endl; return; } int ListaVacia(cc lista) { return (lista == NULL); } void menu() { system("CLS"); cout <<endl<<endl<<endl; cout<<" (a) Agregar "<<endl; cout<<" (e) Imprimir "<<endl; cout<<" (s) Fin "<<endl; cout<<" Opcion --> :"; calificacion = cin.get(); return; }

Como funciona el programa?


25 Do { . . . . 64 } while (calificacion != EOF)

El programa presenta en la lin 25 un ciclo do while que se rompe solo cuando la variable de entrada calificacin sea igual a EOF (fin de archivo o ctrl z)
Lo primero que se hace dentro del ciclo es invocar a la funcin men() la cual despliega el men selectivo y lee desde el teclado un carcter (lin109 con la funcin cin.gen)

100.void menu() 101{ 102 system("CLS"); 103 cout <<endl<<endl<<endl; 104 cout<<" (a) 105 cout<<" (e) 107 cout<<" (s) 108 cout<<" 109 calificacion = cin.get(); 110 return; 111}

Agregar "<<endl; Imprimir "<<endl; Fin "<<endl; Opcion --> :";

27switch ( calificacion ) { // switch anidada en un while 28 29 case 'A': 30 case 'a': 31 32 cout << " Indique el valor (-1:fin) .." <<endl; 33 cin >> dato; 34 Insertar(&c,dato); 35 break; 36 37 case 'E': 38 case 'e': 39 Imprimir(c); 40 system("pause"); 41 break; 42 43 case 'f': 44 case 'F': 45 calificacion = EOF; 46 break; 47 case '\n': // ignora nuevas lneas, 48 case '\t': // tabuladores, 49 case ' ': 50 case EOF: 51 break; 52 case 's': 53 case 'S':// sale de switch 54 calificacion = EOF; 55 break; 56 default:// atrapa todos los dems caracteres 57 cout << "Se introdujo una letra incorrecta." 58 << "Introduzca una nueva letra." << endl; 59 break; 60 } // fin de switch 61 62 } while (calificacion != EOF);// fin de while

Dependiendo del carcter ledo a traves de la funcin men() se entra en una estructura de case que bifurca a una funcin especfica de acuerdo al carcter ledo. De esta forma si el carcter leido es a o Ase invoca la funcin Insertar (lin 34), al regresar la instruccin break (lin 35) rompe el flujo secuencial de control y enva la ejecucin al final del case (lin 60)

PROYECTO DE DESARROLLO El proyecto consiste en ampliar el men visto en esta gua con las siguientes opciones:

(S ) (R ) (M) (I ) (A ) (M) (S )

Suma Resta Multiplica Intercambia Agregar Mostrar Salir Opcin

SUMA: Suma el contenido de la primera posicin de a pila con el contenido de la segunda posicin de la pila y el resultado se convierte en la primera posicin de la pila. Los operadores contenidos en la primera y segunda posicin de la pila desaparecen mantenindose intacta el resto de la lista. RESTA: resta al contenido de la primera posicin de a pila el contenido de la segunda posicin de la pila y el resultado se convierte en la primera posicin de la pila. Los operadores contenidos en la primera y segunda posicin de la pila desaparecen mantenindose intacta el resto de la pila. MULTIPLICA: Suma el contenido de la primera posicin de la pila con el contenido de la segunda posicin de la pila y el resultado se convierte en la primera posicin de la pila. Los operadores contenidos en la primera y segunda posicin de la pila desaparecen mantenindose intacta el resto de la lista. INTERCAMBIA: Cambia el contenido de la primera posicin de la pila con el contenido de la segunda posicin de la pila y viceversa. Se mantiene intacta el resto de la lista. AGREGAR, MOSTRAR Y SALIR : Igual a lo antes expuesto en la gua.

Todo procedimiento debe verificar que la lista dispone de los elemento suficientes para elaborar las operaciones antes sealadas.

Se debe entregar informe por grupo contentivo de:

1. Explicacin del algoritmo general y de cada procedimiento (5ptos.) 2. Diagrama esquemtico en donde se visualice como se ejecutan las secuencias de cada operacin. (5ptos.) 3. Cdigo en lenguaje C (5ptos.) 4. Corrida. (5ptos.)

You might also like