You are on page 1of 19

Instituto Universitario del Prado

Asignatura: Tema 4: Fundamentos de Programacin Programacin modular: procedimientos y funciones

4.1.- Introduccin a la programacin modular El programa se divide en mdulos, cada uno de los cuales ejecuta una nica actividad o tarea y se analizan, codifican y ponen a punto por separado y de manera independiente. Cada programa contiene un mdulo central llamado principal que transfiere el control a los sub-mdulos segn sea necesario, de modo que ellos puedan ejecutar sus funciones. La independencia en los mdulos radica en que ninguno de ellos puede tener acceso directo a cualquier otro, con excepcin del mdulo al que llama y sus propios sub-mdulos. Segn el lenguaje de programacin utilizado, a los mdulos se les denomina de cualquiera de las siguientes maneras: Subrutinas Procedimientos Secciones

La programacin modular est ntimamente ligada con la programacin descendente (top-down) que descompone un problema en una serie jerrquica de niveles de complejidad decreciente.

Mtro. Alejandro Salazar Guerrero

1/18

Un subprograma constituye una serie de instrucciones escritas independientemente del programa principal. Este subprograma est ligado al programa principal mediante un proceso de transferencia/retorno: Transferencia: el control de ejecucin se pasa al subprograma en el momento en que se requieren sus servicios. Retorno: el control de ejecucin se devuelve al programa principal cuando el subprograma termina.

/*Programa que calcula y muestra el resultado de la suma, resta, multiplicacin o divisin de dos nmeros introducidos por el usuario, segn la opcin elegida*/ #include<stdio.h> //Librera estndar de entradas y salidas #include<stdlib.h> //Librera estndar. float num1, num2; //Variables globales num1 y num2 void leer() //Definicin de la funcin leer { //Inicio del cuerpo de la funcin printf(Ingrese valor 1: ); //Solicita el valor del primer dato scanf(%f,&num1); //Lee el dato y lo guarda en la variable num1 printf(Ingrese valor 2: ); //Solicita el valor del segundo dato scanf(%f,&num2); //Lee el dato y lo guarda en la variable num2 } //Fin de la funcin void sumar() //Definicin de la funcin sumar { //Inicio del cuerpo de la funcin float suma; //Variable local suma suma = num1 + num2; //Operacin para calcular suma printf(Suma = %.2f\n,suma); //Imprime en pantalla el valor de suma } //Fin del cuerpo de la funcin void restar() //Definicin de la funcin restar { //Inicio del cuerpo de la funcin float resta; //Variable local resta resta = num1 num2; //Operacin para calcular resta printf(Resta = %.2f\n,resta); //Imprime en pantalla el valor de resta } //Fin del cuerpo de la funcin void multiplicar() //Definicin de la funcin multiplicar { //Inicio del cuerpo de la funcin float mult; //Variable local mult mult = num1 * num2; //Operacin para calcular multiplicacin printf(Multiplicacion = %.2f\n,mult); //Imprime en pantalla el valor de mult

Mtro. Alejandro Salazar Guerrero

2/18

} //Fin del cuerpo de la funcin

4.2. Funciones Una funcin es un conjunto de lneas de cdigo que realizan una tarea especfica y puede retornar un valor. Las funciones pueden tomar parmetros que modifiquen su funcionamiento. Las funciones son utilizadas para descomponer grandes problemas en tareas simples y para implementar operaciones que son comnmente utilizadas durante un programa y, de esta manera, reducir la cantidad de cdigo. Cuando una funcin es invocada se le pasa el control a la misma, una vez que esta finaliz con su tarea el control es devuelto al punto desde el cual la funcin fue llamada.

Ejemplo de una funcin Se considerar el caso en el cual se desea crear la funcin cuadrado(), que deber devolver el cuadrado de un nmero real (de punto flotante); es decir, cuadrado() aceptar nmeros de punto flotante y regresar una respuesta como nmero flotante. Aunque para la funcin que veremos, el tipo de retorno coincide con el tipo de parmetro pasado, algunas veces las cosas pueden cambiar; es decir, no es obligatorio que una funcin reciba un parmetro de un tipo y tenga que regresar una respuesta de dicho tipo. //regresar el cuadrado de un nmero double cuadrado(double n) { return n*n; } Parmetros

Mtro. Alejandro Salazar Guerrero

3/18

Normalmente, las funciones operan sobre ciertos valores pasados a las mismas ya sea como constantes literales o como variables; aunque se pueden definir funciones que no reciban parmetros. Si en una declaracin de funcin se declaran parmetros por referencia, a los mismos no se les podrn pasar valores literales, ya que las referencias apuntan a objetos (variables o funciones) residentes en la memoria. Por otro lado, si un parmetro es declarado para ser pasado por valor, el mismo puede pasarse como una constante literal o como una variable: Los parmetros pasados por referencia pueden ser alterados por la funcin que los reciba. Los parmetros pasados por valor o copia no pueden ser alterados por la funcin que los recibe, es decir, la funcin puede manipular a su antojo al parmetro, pero ningn cambio hecho sobre este se reflejar en el parmetro original.

Parmetros por valor La funcin cuadrado(), indicada anteriormente en este texto, es un clsico ejemplo que muestra el paso de parmetros por valor. En este sentido la funcin cuadrado() recibe una copia del parmetro n. En la misma funcin se puede observar que se realiza un clculo ( n*n ). Sin embargo, el parmetro original no sufrir cambio alguno, este seguir siendo cierto aun cuando dentro de la funcin hubiera una instruccin parecida a n = n * n; o n*=n;. Parmetros por referencia Para mostrar un ejemplo del paso de parmetros por referencia, se retomar el caso de la funcin cuadrado, salvo que en esta ocasin cambiaremos ligeramente la sintaxis para definir la misma: // regresar el cuadrado de un nmero double cuadrado2(double &n) { n *= n; return n; } Al poner a prueba las funciones cuadrado() y cuadrado2() se podr verificar que la primera de estas no cambia el valor del parmetro original, mientras que la segunda s lo hace. Llamar a una funcin

Para llamar a la funcin cuadrado() vista anteriormente, podemos emplear: cout << cuadrado(25); cout << cuadrado(X); R = cuadrado(X); // guardar en R el cuadrado de X Funciones void

Mtro. Alejandro Salazar Guerrero

4/18

Bajo ciertas circunstancias se desear escribir funciones que no regresen valor alguno, lo cual sera algo parecido a escribir procedures en Pascal. Para ello, podemos declarar a la funcin como void. La palabra reservada void es utilizada para declarar funciones sin valor de retorno y tambin para indicar que una funcin especfica no requiere de parmetros; por ejemplo, la funcin pausa() que se ver en seguida, no devolver valor alguno y la misma no requiere de parmetros. // esta funcin requiere de la librera iostream void pausa(void) { cout << "Por favor presione <Enter> HOLA..."; cin.get(); cin.ignore(255, '\n'); // rechazar caracteres introducidos antes de <Enter> } Cabe aclarar que el uso de la palabra void dentro de los parntesis es opcional al momento de declarar una funcin. As, la funcin pausa() podra haberse declarado como void pausa(), y la misma puede invocarse como: pausa();. Funciones de tipo puntero En muchas ocasiones se desea que ciertas funciones regresen una referencia o puntero hacia un tipo especfico de dato, sea este estructurado o no, en lugar de un valor especfico. En tales casos, la funcin se deber declarar como para que regrese un puntero. Por ejemplo, supongamos que deseamos crear una funcin para convertir un nmero entero en notacin decimal a una cadena de caracteres en forma de nmeros binarios, luego, la funcin mencionada podra escribirse para que reciba el nmero entero como parmetro y regrese un puntero a una cadena de caracteres conteniendo la conversin. Para ser ms puntuales, vamos a escribir un programa en el cual se ver la funcin binstr(), y cuyo objetivo ser precisamente convertir nmeros decimales en cadenas binarias. Es necesario observar que en la sintaxis para declarar funciones tipo puntero se debe de poner el smbolo. #include <iostream> #include <string.h> using namespace std; // declaracin de prototipo char *binstr(unsigned int); // punto de prueba int main() { int n = 128; cout << "decimal = " << n << ", binario = " << binstr(n) << endl;
Mtro. Alejandro Salazar Guerrero 5/18

cin.get(); } // definicin de funcin binstr() // nota: esta funcion requiere de la librera estndar string char *binstr(unsigned int n) { static char buffer[65]; int i = 0; strcpy(buffer, "0"); if (n > 0) { while (n > 0) { buffer[i] = ( n & 1 ) + '0'; i++; n >>= 1; } buffer[i] = '\0'; strrev(buffer); } // fin (n > 0) return buffer; } Variables estticas y automticas Dentro de una funcin, las variables y/o constantes pueden ser declaradas como: auto (por omisin): las variables automticas pierden su valor entre las llamadas; o static: si una variable dentro de una funcin es declarada como esttica significa que la misma retendr su valor entre las llamadas a la funcin.

En el programa anterior puede verse que el arreglo de caracteres (buffer[65]) se ha declarado como esttico para garantizar que dicho buffer retenga los datos an despus de que la funcin termine. En el mismo ejemplo, si el buffer no se declara como esttico, el contenido del mismo podra ser destruido al salir de la funcin y los resultados obtenidos podran ser no deseados. Parmetros constantes Los parmetros usados por una funcin pueden declararse como constantes (const) al momento de la declaracin de la funcin. Un parmetro que ha sido declarado como constante significa que la funcin no podr cambiar el valor del mismo (sin importar si dicho parmetro se recibe por valor o por referencia). Por ejemplo: int funcionX( const int n ); void printstr( const char *str );
Mtro. Alejandro Salazar Guerrero 6/18

Parmetros con valor por defecto Los parmetros usados por una funcin pueden declararse con un valor por defecto. Un parmetro que ha sido declarado con valor por defecto es opcional a la hora de hacer la llamada a la funcin. Por ejemplo, con la siguiente funcin: void saludo( char* mensaje = "Hola sudafrica 2010" );

La misma puede ser invocada como: saludo(); // sin parmetro saludo("Sea usted bienvenido a C++"); // con parmetro Como un ejemplo adicional, consideremos el caso de la funcin binstr() del programa funciones01, a fin de modificarla para que sirva para convertir nmeros decimales en cadenas numricas y cuya base de conversin sea pasada como parmetro. Es decir, la funcin de la que estamos hablando podr convertir nmeros decimales a: binario, octal, decimal, hexadecimal, etc.; y la nica condicin ser que la base indicada se encuentre entre el 2 y el 36, inclusive. Considerando que la funcin servir para convertir nmeros a cualquier representacin, la nombraremos como numstr() en lugar de binstr(). Si la funcin es invocada sin el parmetro base, regresar una cadena de dgitos decimales. #include <iostream> #include <stdlib.h> using namespace std; // declaracin de prototipo char *numstr(unsigned int, const int base = 10); // punto de prueba int main() { int n = 128; cout << "decimal = " << n << ", binario = " << numstr(n, 2) << endl; cout << "decimal = " << n << ", octal.. = " << numstr(n, 8) << endl; cin.get(); } // definicin de funcin numstr() // nota: esta funcion requiere de la librera stdlib.h

Mtro. Alejandro Salazar Guerrero

7/18

char *numstr(unsigned int n, const int base) { static char buffer[65]; itoa(n, buffer, base); return buffer; }

Parmetros de tipo puntero Anteriormente se mencion que en C++ los parmetros a una funcin pueden pasarse por valor o por referencia, al respecto, podemos agregar que los parmetros tambin pueden pasarse como punteros. El paso de parmetros de punteros es bastante parecido al paso de parmetros por referencia, salvo que el proceso de los datos dentro de la funcin es diferente. Por ejemplo, las funciones: void referencia( int &X ) { X = 100; } void puntero( int *X ) { *X = 100; } Ambas reciben un puntero o referencia a un objeto de tipo entero, por lo que cualquiera de las funciones del ejemplo puede cambiar el valor de la variable entera apuntada por X. La diferencia radica en la forma en que cada una de las mismas lleva cabo la tarea. Si en la funcin puntero() en lugar de usar *X = 100; se usara X = 100; se le asignara 100 al puntero X, ms no al objeto apuntado por X, y esto podra ser la causa de que el programa se terminara de manera abrupta. Parmetros estructurados Al igual que cualquier otro tipo los parmetros de tipo estructurado pueden pasarse por valor o por referencia. Sin embargo, puede suceder que si una estructura es pasada por valor, el compilador muestre una advertencia (warning), indicando que se ha pasado por valor una estructura. Considerando que el paso de estructuras por valor es permitido, es posible ignorar la advertencia, pero lo mejor es pasar estructuras por referencia. Si una estructura muy grande es pasada por valor, puede suceder que se agote la memoria en el segmento de pila (Stack Segment ), aparte de que la llamada a la funcin ser ms lenta. Para ver un ejemplo, consideremos el caso del siguiente tipo estructurado: struct empleado { char nombre[32]; int edad; char sexo; };

Mtro. Alejandro Salazar Guerrero

8/18

La funcin para imprimir variables del tipo empleado puede escribirse de las tres maneras siguientes: void ImprimeEmpleadoV( empleado e) { cout << "Nombre: " << e.nombre << endl; cout << "Edad: " << e.edad << endl; cout << "Sexo: " << e.sexo << endl; } // Parametro empleado pasado por referencia void ImprimeEmpleadoR( empleado &e ) { cout << "Nombre: " << e.nombre << endl; cout << "Edad: " << e.edad << endl; cout << "Sexo: " << e.sexo << endl; } // Parametro empleado pasado como puntero void ImprimeEmpleadoP( empleado *e ) { cout << "Nombre: " << e->nombre << endl; cout << "Edad: " << e->edad << endl; cout << "Sexo: " << e->sexo << endl; } Funciones sobrecargadas C++, a diferencia del C estndar, permite declarar funciones con el mismo nombre y a esto se conoce como sobrecarga de funciones. Las funciones sobrecargadas pueden coincidir en tipo, pero al menos

Mtro. Alejandro Salazar Guerrero

9/18

uno de sus parmetros tiene que ser diferente. En todo caso, si usted trata de declarar funciones sobrecargadas que coincidan en tipo y nmero de parmetros el compilador no se lo permitir. A manera de ejemplo, se considerar el caso de dos funciones cuyo nombre ser divide. Ambas regresarn el cociente de dos nmeros, salvo que una de ellas operar sobre nmeros enteros y la otra lo har sobre nmeros reales (de punto flotante). Cabe sealar que, cuando en los programas se hace una llamada a una funcin sobrecargada, el compilador determina a cul de las funciones invocar, con base en el tipo y nmero de parmetros pasados a la funcin.

#include <iostream.h> #include <stdlib.h> using namespace std; // divide enteros int divide(int a, int b) { cout << "divisin entera" << endl; return ( (b != 0) ? a/b : 0); } // divide reales double divide(double a, double b) { cout << "divisin real" << endl; return ( (b != 0) ? a/b : 0); } // punto de prueba int main() { cout << divide(10, 3) << endl; cout << divide(10.0, 3.0) << endl; cin.get(); } Nmero variable de parmetros En C,C++ es posible crear funciones que operen sobre una lista variable de parmetros; es decir, donde el nmero de parmetros es indeterminado. En esta seccin se mostrar un ejemplo de la manera en que se pueden crear funciones para manejar tales asuntos. Para ello, se utilizarn tres macros soportadas por C++:

Mtro. Alejandro Salazar Guerrero

10/18

1. 2. 3.

va_list: puntero de argumentos va_start: inicializar puntero de argumentos va_end: liberar puntero de argumentos

La sintaxis que se usar para declarar funciones con lista de parmetros variables es: 1) 2) Dnde: 1. 2. 3. 4. tipo: es el tipo regresado por la funcin. Nombrefuncion: es el nombre de la funcin. int num: es el nmero de parmetros que la funcin procesar. ... esta notacin se emplea para indicar que el nmero de parmetros es variable tipo nombrefuncion(...) tipo nombrefuncion(int num, ...)

La primera forma de declaracin es realmente variable en cuanto al nmero de parmetros a procesar, por lo que en estos casos se debe establecer el mecanismo para determinar cundo se ha procesado el ltimo de los argumentos. En el segundo tipo de declaracin el nmero total de parmetros a procesar es igual al valor del parmetro num. Por ejemplo, en el siguiente programa, se define una funcin ( printstr ) que despliega una lista variable de cadenas de caracteres: #include <iostream.h> #include <stdarg.h> // despliega una lista de cadenas, la ultima debe ser NULL void printstr(...) { va_list ap; char *arg; va_start(ap, 0); while ( (arg = va_arg(ap, char*) ) != NULL) { cout << arg; } va_end(ap); } int main() { printstr("Hola, ", "Esta es\n", "una prueba\n", NULL);
Mtro. Alejandro Salazar Guerrero 11/18

cin.get(); return 0; } En el programa que se listar a continuacin se define la funcin suma(), misma que operar sobre listas de nmeros enteros. La funcin devolver la suma de dichos nmeros: #include <iostream>//entrada y salida #include <stdarg.h> using namespace std; // Esta funcin opera sobre una lista variable de nmeros enteros int suma( int num, ... ) { int total = 0; va_list argptr; va_start( argptr, num ); while( num > 0 ) { total += va_arg( argptr, int ); num--; } va_end( argptr ); return( total ); } int main() { cout << suma(4, 100, 200, 300, 400) << endl; cin.get(); return 0; }

4.3. Procedimientos Son subprogramas, es decir, mdulos que forman parte de un programa y realizan una tarea especfica. Un procedimiento puede tener sus propias variables que se declaran en la seccin var del propio procedimiento y se denominan variables locales. La casilla de memoria para estas variables se crea cada vez que el procedimiento es llamado y se borra al salir del mismo. Por ello, las variables locales para un procedimiento slo se pueden usar en el cuerpo del procedimiento y no en el cuerpo principal del programa.

Mtro. Alejandro Salazar Guerrero

12/18

La declaracin de un procedimiento es similar a la de una funcin. Las pequeas deferencias se deben a que el nombre del procedimiento no se encuentra asociado a resultado alguno. La declaracin de un procedimiento expresado en pseudocdigo es: procedimiento <nombre_procedimiento> (lista_de_parmetros_formales)[ Var declaraciones_locales ] inicio acciones fin_procedimiento Los parmetros que aparecen en la declaracin del procedimiento se denominan parmetros formales, mientras que los parmetros que se utilizan cuando se llama al procedimiento, se denominan parmetros actuales o reales.

Llamado de un procedimiento Para llamar a un procedimiento se realiza con una instruccin llamar_a o bien directamente con el nombre del procedimiento: [llamar_a]<nombre_procedimiento>[( parmetros_actuales)] El procedimiento puede ser llamado desde el algoritmo principal o desde cualquier otro subalgoritmo. Por ejemplo: Procedimiento mitad(E entero : n) Var Real : m inicio m <-- n/2 escribir(La mitad de + n + es + m) fin_procedimiento algoritmo calcular_mitad var entero: num inicio escribir(Introduce un nmero para hallar su mitad) leer(num) llamar_a mitad(num) fin Diferencia entre funciones y procedimientos

Mtro. Alejandro Salazar Guerrero

13/18

Una funcin devuelve un nico valor y un procedimiento puede devolver 0, 1 N, a travs de los parmetros. Ninguno de los resultados devueltos por el procedimiento se asocian a su nombre, como ocurra con la funcin. La llamada a una funcin siempre forma parte de una expresin y la llamada a un procedimiento es una instruccin que por s sola no necesita instrucciones.

4.4. Visibilidad de las variables La visibilidad de un identificador es la regin de cdigo fuente desde la que se puede legalmente acceder al objeto que le es asociado al primero. mbito y visibilidad coinciden generalmente, aunque pueden darse circunstancias en que un objeto aparezca oculto (invisible) temporalmente, debido a la presencia de un identificador duplicado. El objeto existe, pero el identificador original no puede ser utilizado para accederlo hasta que el identificador duplicado se encuentre terminado. Cabe sealar que la visibilidad no puede exceder al mbito, pero este puede exceder a la visibilidad. Existen siete categoras para la visibilidad de un identificador: 1) 2) 3) 4) 5) 6) 7) Sentencia Bloque (o local) Funcin Prototipo de funcin Fichero Clase Espacio de nombres

Por ejemplo: ... {

Mtro. Alejandro Salazar Guerrero

14/18

int i; char ch; // auto por defecto i = 3; // int i y char ch, en mbito y visibles ... { double i; i = 3.0e3; // double i en mbito y visible // int i=3 en mbito pero oculto ch = 'A'; // char ch en mbito y visible } // double i es terminada aqu // double i fuera de mbito i += 1; // int i visible, i == 4 ... // char ch todava en mbito y visible (ch = 'A') } // int i y char ch son terminados aqu ... // int i y char ch fuera de mbito Se aplican reglas especiales para los nombres de clases y miembros ocultos de clase. Bajo ciertas condiciones, los operadores de acceso permiten acceder identificadores ocultos cuando son miembros de clase. Variables globales Las variables globales a un fichero se declaran fuera de cualquier bloque, funcin o clase. La sintaxis de la declaracin es idntica a la de las variables locales, solo cambia su situacin. El hecho de colocarlas al principio evita tener que hacerlas visibles dentro de cada funcin con una declaracin externa de cada variable. La regla es que si la declaracin de una variable externa ocurre antes que su uso en alguna funcin particular, entonces no hay necesidad de una declaracin externa de la variable dentro de la funcin; por ejemplo: extern x; // punto de declaracin de x ... void func1(int y) { x = x+y; // correcto x es visible } void func2(int y) { z = z+y; // incorrecto z no es visible extern z; z = z+y; // correcto z es ahora visible } El mbito de una variable global abarca desde el punto de declaracin hasta el final del fichero, por lo que tradicionalmente se suelen declarar al principio, junto con los prototipos de las funciones, ya que en
15/18

Mtro. Alejandro Salazar Guerrero

caso contrario, hay que declararlas dentro de cada funcin que las invoque; es decir, avisar a cada funcin que la variable en cuestin es externa. Puesto que C++ no permite declaracin de funciones dentro de funciones. Sus identificadores son globales al fichero en que se han declarado. Las funciones tienen mbito global. Lo que s se permite son prototipos de funciones dentro de otras funciones que las invocan. Los prototipos son declaraciones, no definiciones. Por supuesto, si las variables globales a un fichero deben ser vistas desde otros ficheros, es necesario declararlas al principio como externas en los otros ficheros. Por esta razn y por comodidad, se acostumbra agrupar todas las declaraciones de variables y funciones externas en unos ficheros que actan como "repositorios" de declaraciones y definiciones que son incluidos mediante #include al principio de cada fuente. De esta manera no se olvida ningn extern. Por esta razn, a tales ficheros se les denomina de cabecera. Por una larga tradicin de C, las declaraciones de las funciones de las Libreras Estndar se agrupan en una serie de ficheros de nombres conocidos. Los correspondientes a las libreras que se mantienen por compatibilidad con el antiguo C tienen la terminacin .h, de Header (cabecera en ingls). Por defecto, las variables externas y las funciones tiene la propiedad de que todas las referencias a sus nombres (incluso desde mdulos compilados separadamente), referencian a la misma entidad; es decir, tienen enlazado externo. Aunque desde cierta ptica, el empleo de variables globales facilita algunas cosas, como lo es el hecho de que hay que pasar menos parmetros a las funciones; el abuso de la mismas constituye una prctica perjudicial, toda vez que los programas se hacen difciles de manejar e interpretar, existe ms posibilidad de colisiones de nombres y se poluciona el espacio global. Es preferible que todos los datos que se necesitan en una funcin estn definidos dentro del cuerpo o en su lista de parmetros. Cabe reiterar que una variable global declarada static solo es visible desde el punto de declaracin hasta el final del fichero y solo en ese fichero. Esto aplica tambin para las funciones.

4.5. Intercambio de Informacin: paso de parmetros Al momento de crear funciones y procedimientos puede que sea necesario que trabajemos con datos que se encuentran alojados en el programa que los llama, para eso existen los parmetros. Los parmetros son valores que se envan a un procedimiento o funcin para que stos puedan trabajar con ellos. Para utilizar los parmetros en un procedimiento o funcin debemos declarar el tipo de dato y su identificador, en forma exactamente igual a la declaracin de una variable. A continuacin se puede apreciar el programa del rea del tringulo, en el cual se pasan por parmetros los datos de base y altura:

Mtro. Alejandro Salazar Guerrero

16/18

#include <stdio.h> #include <stdlib.h> void areatriangulo (float base, float altura) { printf("El rea es: %2.2f \n",(base*altura)/2); } int main(int argc, char *argv[]) { float base, altura; printf("Introduce base: "); scanf("%f",&base); printf("Introduce altura: "); scanf("%f",&altura); areatriangulo(base,altura); system("PAUSE"); return 0; } Es muy importante que las variables se pasen en el mismo orden que como se han definido en los parmetros. De lo contrario, se pueden tener resultados inesperados en la ejecucin del programa. Los identificadores son palabras en lenguaje humano legible mediante el cual se manejan celdas de memoria; da igual como se llamen en el programa, en las funciones y en los procedimientos.

Paso de parmetros por valor y por referencia El paso de parmetros a procedimientos y funciones es un recurso bastante potente de cara a trabajar con datos. Adems, es posible pasar estos parmetros de varias formas, por valor o por referencia; esto se especifica cuando definimos el procedimiento o funcin. Mediante el paso por valor, el procedimiento o funcin recibe los valores indicados para poder trabajar con ellos, su declaracin es la siguiente: Procedimiento - void areatriangulo (float base, float altura) Funcin - float areatriangulo (float base, float altura) En algunas ocasiones ser necesario modificar algunos de los datos que se han pasado en los parmetros, para lo cual es posible declarar los parmetros de tal forma que se puedan modificar, a esto se le llama paso por referencia.

Mtro. Alejandro Salazar Guerrero

17/18

Gracias al paso por referencia un procedimiento o funcin no slo realiza unas operaciones y devuelve (en el caso de las funciones) un valor, sino que tambin puede modificar los valores que se pasan como parmetros. Para poder realizar el paso de parmetros por referencia es necesario que en la declaracin del procedimiento o funcin se especifique el espacio de memoria donde se encuentra alojado el dato. Esto se realiza de la siguiente manera: Procedimiento - void areatriangulo (float *base, float *altura) Funcin - float areatriangulo (float *base, float *altura) Lo que se acaba de definir como parmetros no son las variables en s, sino un puntero que apunta a la direccin de memoria donde se encuentra alojado el valor, as podremos modificarlo. Para llamar a un procedimiento o funcin pasando los parmetros por valor se hace de la forma que hemos visto: Procedimiento - areatriangulo(base, altura); Funcin - area=areatriangulo(base, altura); De la siguiente manera se llama a un procedimiento o funcin pasando los parmetros por referencia: Procedimiento - areatriangulo(&base, &altura); Funcin - area=areatriangulo(&base, &altura); As lo que pasamos como parmetros no es el valor de la variable, sino la direccin de memoria donde se encuentra el dato. De sta forma, el procedimiento o funcin podr modificar su valor directamente. Veamos el caso de un programa que intercambia los valores de dos variables, en uno utilizaremos parmetros por valor y en el otro por referencia: Por valor: #include <stdio.h> #include <stdlib.h> void intercambio(int num1, int num2){ int aux; aux=num1; num1=num2; num2=aux; printf("El intercambio es: num1=%d num2=%d\n",num1,num2); } int main(int argc, char *argv[]) {
Mtro. Alejandro Salazar Guerrero 18/18

int num1=3, num2=5; printf("Vamos a intercambiar: num1=%d num2=%d\n",num1,num2); intercambio(num1,num2); printf("El resultado tras el intercambio es: num1=%d num2=%d\n",num1,num2); system("PAUSE"); return 0; } Por referencia: #include <stdio.h> #include <stdlib.h> void intercambio(int *num1, int *num2){ int aux; aux=*num1; *num1=*num2; *num2=aux; printf("El intercambio es: num1=%d num2=%d\n",*num1,*num2); } int main(int argc, char *argv[]) { int num1=3, num2=5; printf("Vamos a intercambiar: num1=%d num2=%d\n",num1,num2); intercambio(&num1,&num2); printf("El resultado tras el intercambio es: num1=%d num2=%d\n",num1,num2); system("PAUSE"); return 0; } Al compilar ambos cdigos y observar la diferencia es donde radica el potencial del paso por valor y por referencia.

Mtro. Alejandro Salazar Guerrero

19/18

You might also like