UNIVERSIDAD DON BOSCO FACULTAD DE ESTUDIOS TECNOLÓGICOS ESCUELA DE COMPUTACION CICLO: 02/ 2011 Nombre de la Practica: Lugar de Ejecución: Tiempo Estimado: MATERIA: GUIA DE LABORATORIO #10 Funciones definidas por el programador Parte 2 Centro de Computo 2 horas y 30 minutos Introducción a la Programación I. OBJETIVOS Que el estudiante: • Determine el diseño mas eficiente para una función (¿Argumentos por valor, por referencia?, ¿devuelve o no valor alguno?, etc.). • Manipule las diversas maneras de ¿cómo realizar la llamada a una función desde otra función? • Programe el paso de parámetros por Valor y por Referencia a una función. • Diseñe e implemente funciones de tipo Recursivas II. INTRODUCCION TEORICA PARÁMETROS DE UNA FUNCIÓN/PROCEDIMIENTO Existen dos tipos de pasar los datos como parámetros: Por referencia y por Valor Paso de parámetros por valor (también llamado paso por copia). Significa que cuando C++ compila la función, el código que llama a otra función realiza una “copia” de los valores de los parámetros. Si se cambia el valor de un parámetro (variable local), este cambio solamente influye dentro del código de esa función, nada fuera de ella. Ejemplo: int ventasMayores(i nt a, int b) //paso de parámetros por valor El método de pasar parámetros por defecto de C es el por valor (excepto cuando se pasen arreglos. Los arreglos se pasan por dirección o referencia, como lo vera mas adelante). Paso de parámetros por referencia. Cuando una función debe modificar el valor del parámetro recibido y devolver este valor modificado a la función llamadora, se ha de utilizar el método de paso de parámetro por referencias o dirección. En este método el compilador pasa la dirección de memoria del valor del parámetro a la función. Cuando se modifica el valor del parámetro (la variable local), este valor queda almacenado en la misma dirección de memoria, por lo que al retornar a la función llamadora la dirección de la memoria donde se almacenó el parámetro contendrá el valor modificado. Ejemplo: 1/7 Guía #10: Funciones definidas por el programador Parte 2 void intercambio(int &a, int &b) Una referencia a una variable es un "alias/apuntador" de esa variable. Para indicarle a C++ que estamos hablando de una referencia y no una variable común, anteponemos al nombre el carácter ampersand (&). VARIABLES GLOBALES Y LOCALES En C++ está permitido declarar variables en cualquier parte del código fuente. Además de pasar variables como parte del argumento de una función, también es posible declarar variables dentro del cuerpo de la función, a este tipo de variables se les llama locales ya que sólo son útiles dentro del cuerpo de la función. Los parámetros utilizados por una función se consideran como variables de tipo local. Es decir que le sirven a la función para realizar sus procesos y copiar el valor de los parámetros con los cuales es llamada. A las variables que declaramos fuera del cuerpo de cualquier función se dice que tienen un alcance global y por lo tanto estas funciones están disponibles para cualquier función del programa, incluyendo a main(). Las variables locales que tienen el mismo nombre que las globales: a) no cambian el valor de las globales b) una variable local con el mismo nombre que una variable global oculta a la variable global. RECURSIVIDAD La recursividad es una técnica de programación que consiste en lo siguiente: + Se elabora una función que se llama a sí misma de forma repetitiva, hasta que satisface una “Condición de Parada (CP)”. + Esta CP determina ¿Hasta cuando se seguirá llamando la función a sí misma?. Esta condición se le conoce como la “solución trivial al problema”, porque al cumplirse provoca que se comience a retornar valores a las llamadas anteriores de la misma función, hasta finalizar con la función que realizo la llamada inicial. ¿Cómo se construye una función de manera Recursiva? Una función recursiva sigue la estrategia del “divide y vencerás”, dividiendo la definición de la misma en dos partes: a) La parte que la función no sabe cómo resolver. La parte que la función no sabe cómo resolver debe replantear el problema original de modo que la solución sea más simple, o más pequeña que la versión original del problema. Como el problema todavía no está resuelto, sino que solamente se ha replanteado, se hace una nueva llamada a la misma función para que intente resolver el problema más pequeño. Si todavía no lo puede resolver, se vuelve a replantear, siempre de forma más simple, hasta que llegue un momento en que el problema planteado sea justamente igual al que si puede resolver. b) La parte que la función sabe cómo resolver En ese momento de la función, esta devolverá a la llamada anterior de la función un resultado exacto, y cada llamada anterior devolverá el resultado a las llamadas recursivas que le preceden. ¿Cuál es el objetivo de la condición de parada CP dentro de una función Recursiva? La condición (o condiciones) de parada a cumplirse para que un problema se pueda resolver de forma recursiva hacen que la función pueda escribirse en forma recursiva, llamándose a si misma y que la especificación del problema tenga una solución trivial. Esta solución trivial permite establecer una condición de paro a las llamadas recursivas de la función. Introducción a la Programación 2 Guía #10: Funciones definidas por el programador Parte 2 III. MATERIALES Y EQUIPO Para la realización de la guía de práctica se requerirá lo siguiente: No. Requerimiento 1 Guía de Laboratorio #10 de IP 2 Disquete ó Memoria USB 3 PC con DEV-C++ Cantidad 1 1 1 IV. PROCEDIMIENTO Ejemplo #1: Programa que utiliza parámetros por referencia en la definición de una función #include<stdio.h> #include<conio. h> //prototipo de funcion void intercambio(int n1,int n2); int main(){ int a,b;//2 valores que ingresa usuario printf("Ingrese 2 numeros:\t"); scanf("%d%d",&a,&b); printf("\nValores originales son:\t%d y %d",a,b); intercambio(a,b); //llamada a la funcion printf("\n\nValores intercambiados son:\t%d y %d",a,b); getch(); }//fin main //definicion de funcion void intercambio(int n1,int n2){ //realiza el intercambio de los parametros recibidos int q;//variable de apoyo para hacer operacion q=n1; n1=n2; n2=q; }//fin de funcion intercambio Luego de digitarlo, proceda a ejecutarlo. Se dará cuenta que no se realiza el intercambio esperado. Esto se debe a que los parámetros n1 y n2 se han definido por valor. Convierta n1 y n2 en parámetros por Referencia, agregando un & a la izquierda de n1 y n2 en ambos encabezados (del prototipo y definición), así: i n t & n 1 , i n t & n 2 . Repita la ejecución y vera que si realiza el intercambio Ejemplo #2: Programa que utiliza parámetros por valor y por referencia en la definición de una función #include<stdio.h> #include<conio. h> void Operar(int n1,int n2, float &div, int &mod);//declaracion de la funcion Introducción a la Programación 3 Guía #10: Funciones definidas por el programador Parte 2 int main(){ int a,b;// valores que ingresa usuario // variables que recibe n s us v alores des de argument os (por referencia) f loat x 1; int x 2; printf("Ingrese 2 numeros:\t"); scanf("%d%d",&a,&b); Operar(a,b,x1,x2); //llamada a la funcion printf("\nLa division y modulo de: %d y %d son:\n”,a,b); printf ("\ t Divis ion= %. 4f\t Modulo: %d", x 1, x 2); getch(); }//fin main void Operar(int n1,int n2, float &div, int &mod){ /* Devuelve en parametros por referencia (s y mod): la division y modulo de la division entre n1 y n2, respectivamente */ div= float(n1)/float(n2); mod=n1 % n2; } Ejemplo #3: Programa que demuestra el uso de variables de alcance global y local /*************************************************************** * Definiendo y utilizando variables globales y locales * ****************************************************************/ #include <iostream> using namespace std; #include <conio.h> int a; // variable entera (a) Global //prototipos de funciones void Funcion1(void); void Funcion2(void); void Funcion3(void); int main(){ a=5; cout<<"Valor INICIAL de variable a es: "<<a; //llamadas a funciones en las cuales no se les envia ningun parametro Funcion1(); Funcion2(); Funcion3(); cout<<"\n\nValor FINAL de variable a : "<<a; getch(); } //definicion de las funciones void Funcion1(void){ char a; //variable caracter (a) Local Introducción a la Programación 4 Guía #10: Funciones definidas por el programador Parte 2 a='w'; cout<<"\nDentro de Funcion1: valor de variable a es\t"<<a; } void Funcion2(void){ a=a*400; cout<<"\nDentro de Funcion3: valor de variable a es\t"<<a; } void Funcion3(void){ float a=2.5; //variable de punt o flotante (a) Local a=a*12; cout<<"\nDentro de Funcion2: valor de variable a es\t"<<a; } IMPORTANTE: Compile, ejecute y analice este programa, para luego responder a estas preguntas: + ¿Por qué lenguaje C no da error al declarar 3 variables con el mismo nombre (a)? + Dado que dentro de cada función se altera el valor de la variable a, ¿Se puede afirmar que las 3 funciones permiten alterar el valor de la variable (a) de alcance Global? Explique Ejemplo #4: Calcular el factorial de un número utilizando recursividad /*************************************************************** * Calcular el factorial de un número utilizando recursividad * ****************************************************************/ #include <stdio.h> #include <conio.h> / / P r o t o t i p o / d e c l a r a c i o n d e l a f u n c i ó n f a c t o r ia l long int factorial(int n); //n: parámetro de entrada, para ingreso del numero para calcular su factorial //valor devuelto: factorial del parámetro n //Definición de funcion principal main main (){ int n; printf ("\t\tPrograma para calculo de Factorial."); //Leer la cantidad entera ingresada por el usuario do{ printf("\n\nEscriba un Numero entero positivo:\t"); scanf("%d",&n); if(n<0){ print f ("\ nNumero incorrec t o, digit e un numero c ero o pos itivo\ n\ n"); } }while(n<0); //Calcula y visualiza el fact orial del n print f("%d! = %d\ n", n, f act orial(n)); // llama a f unct ion f act orial getch(); } //fin funcion //Definición de la función factorial long int factorial(int n){ long fna; //factorial del numero anterior al n recibido Introducción a la Programación 5 Guía #10: Funciones definidas por el programador Parte 2 //Condicion de parada CP if((n == 0)||(n == 1)){ //condición trivial: de retorno de función ret urn 1; } else{ /*Inicio de la Recursividad: Funcion f actorial se vuelve a llamar a si misma con un problema más simple: factorial del término anterior al n actual*/ fna= factorial(n-1); ret urn (n * f na); } } //fin funcion Veamos paso a paso lo que sucede cuando se ejecuta esta función, por ejemplo: factorial(4): 1a Instancia n=4 n>1 salida ← 4 * factorial(3) (Guarda el valor de n = 4) 2a Instancia n>1 salida ← 3*factorial(2) (Guarda el valor de n = 3) 3a Instancia n>1 salida ← 2*factorial(1) (Guarda el valor de n = 2) 4a Instancia n == 1 → retorna 1 3a Instancia (recupera n=2 de la pila) retorna 1*2=2 2a instancia (recupera n=3 de la pila) retorna 2*3=6 1a instancia (recupera n=4 de la pila) retorna 6*4=24 Valor de retorno → 24 Introducción a la Programación 6 Guía #10: Funciones definidas por el programador Parte 2 V. INVESTIGACION COMPLEMENTARIA EJERCICIO 1 (25%): Escriba 2 funciones para convertir grados (la 1era de grados sexagesimales a radianes y otra de radianes a grados) EJERCICIO 2 (45%): En un único código fuente, realice una función por cada una de las tareas a continuación: a) Permita recibir en un parámetro un total de resistencias. Con este total, se debe solicitar al usuario los diferentes valores y al finalizar, se retorna en argumentos de salida: la menor de las resistencias ingresadas y la resistencia equivalente. b) Calcule y retorne el “área total” de una pirámide. Recibe los datos necesarios en parámetros y regresa la respuesta a función que la llama. c) Recibe el sueldo de un empleado, para retornar en argumentos por referencia: descuento del ISSS (8.3%) y de renta (12.7%), el sueldo neto a pagar. Luego permita seleccionar la prueba de cada una, gracias a un menú desde la función principal main. EJERCICIO 3 (30%): Un archivo de cabecera en C/C++ es un archivo con extensión .h y en el mismo se definen un conjunto de funciones. Las funciones de una librería pueden ser utilizadas en algún programa, haciendo referencia a él con la instrucción #include. Investigue ¿Cómo crear su propia librería? y elabore una librería .h propia, con las siguientes funciones: a) Intercambiar el valor de 2 variables b) Retornar el mayor de 3 números enteros c) Limpiar la pantalla Finalmente, desarrolle un ejemplo de programa cpp que implemente su nueva librería. VI. BIBLIOGRAFIA • • • Deitel, Harvey M. y Deitel, Paul J. CÓMO PROGRAMAR EN C++. 1ra Edición. Editorial Mc Graw Hill Pappas, Chris H. y Murray, William H. MANUAL DE REFERENCIA DE VISUAL C++ 6.0. 4ta Edición Editorial Prentice Hall (PEARSON). Joyanes Aguilar, Luís. PROGRAMACIÓN EN C++ - ALGORITMOS, ESTRUCTURAS DE DATOS Y OBJETOS. Editorial McGraw Hill, España, 2000. Introducción a la Programación 7