Punteros Herman Schinca Clase 6 13 de Abril de 2012 Repaso int sumaDoble(int a, int b){ a = 2*a + 2*b; } int main(int argc, char* argv[]){ int a = atoi(argv[1]); int b = atoi(argv[2]); sumaDoble(a,b); printf("El valor de a es %i.\n",a); return 0; } Repaso Nuestra intención era que la función sumaDoble modificara el valor del parámetro a. Sin embargo, el parámetro lo pasamos por copia. El valor que se modifica es el de la copia, no el del parámetro. sumaDoble: pasaje por referencia ¡Pues qué no cunda el pánico! En vez de pasar el valor de la variable a podemos pasar la dirección de memoria en donde se almacena el valor de a. SumaDoble por referencia int sumaDoble(int* a, int b){ *a = 2*(*a) + 2*b; } int main(int argc, char* argv[]){ int a = atoi(argv[1]); int b = atoi(argv[2]); sumaDoble(&a,b); printf("El valor de a es %i.\n",a); return 0; } Referencia paso a paso int sumaDoble(int* a, int b) La función recibirá un puntero a entero y un entero, en lugar de 2 enteros. El puntero a entero indicará la posición de memoria en donde se aloja el valor de a. Referencia paso a paso *a = 2*(*a) + 2*b; a es un puntero a entero. Queremos modificar el valor al que apunta. Para acceder a dicho valor usamos el operador estrella *. * desreferencia el puntero, es decir, obtiene el valor apuntado por el puntero. ¡Pelota al piso! ¿Repasando, qué significa *? Operador * Mismo símbolo, distinta semántica. En el contexto de los punteros, colocado a la izquierda significa “desreferenciación”. En el contexto de las operaciones entre números significa multiplicación. Referencia paso a paso int a = … ; sumaDoble(&a,b); sumaDoble recibe un puntero a entero pero a es un entero. El operador & aplicado a una variable devuelve la dirección de memoria en la que se aloja. Paso a paso ¿Muy complicado, Mostaza? sumaDoble: alternativa int sumaDoble(int* a, int b){ *a = 2*(*a) + 2*b; } int main(int argc, char* argv[]){ int* a; *a = atoi(argv[1]); int b = atoi(argv[2]); sumaDoble(a,b); printf("El valor de a es %i.\n",*a); return 0; } Ejercicio 1 Explique qué hace y por qué hace lo que Ud. dice que hace el siguiente código de C: Ejercicio 1 int main(int argc, char* argv[]){ const int a = 0; int i = 2*a; int x = 10; int* y = &x; y = 0; while(i > 0){ *y = x * (*y); i = i - 1; } printf("El valor de *y es %i.\n",*y); return 0; } El Desafío Final Implemente un algoritmo en C que dado un arreglo de enteros, su tamaño y 2 enteros init y fin, devuelva en init y fin respectivamente las posiciones de inicio y fin de la subcadena del arreglo que constituya la escalera más larga. En caso de empate, devolver la primera. Una escalera es una secuencia de números donde cada uno es el sucesor del anterior. Debe definir y utilizar las siguientes funciones: El Desafío Final int escalera(int arr[], int tam, int pos); void escaleraMasLarga (int arr[], int tam, int* init, int* fin); El Desafío Final La función escalera devuelve la posición en donde termina la escalera que comienza en pos. La función escaleraMasLarga modifica los valores de init y fin poniendo los índices de comienzo y fin de la escalera más larga. El Desafío Final: ejemplos Para los siguientes arreglos se deben devolver los siguientes valores: int a[11] int b[9] int c[5] int d[10] int e[1] int f[7] = {-1,0,1,2,3,5,7,8,9,0,4}; // (0,4) = {-1,0,1,5,7,8,9,0,4}; // (0,2) = {1,3,4,9,1}; // (1,2) = {9,8,7,6,5,4,3,2,1,0}; // (0,0) = {1}; // (0,0) = {1,2,3,4,5,6,7}; // (0,6) ¿Preguntas? A la memoria de Dennis Ritchie: 1941-2011