




































































Prepara tus exámenes y mejora tus resultados gracias a la gran cantidad de recursos disponibles en Docsity
Gana puntos ayudando a otros estudiantes o consíguelos activando un Plan Premium
Prepara tus exámenes
Prepara tus exámenes y mejora tus resultados gracias a la gran cantidad de recursos disponibles en Docsity
Prepara tus exámenes con los documentos que comparten otros estudiantes como tú en Docsity
Encuentra los documentos específicos para los exámenes de tu universidad
Estudia con lecciones y exámenes resueltos basados en los programas académicos de las mejores universidades
Responde a preguntas de exámenes reales y pon a prueba tu preparación
Consigue puntos base para descargar
Gana puntos ayudando a otros estudiantes o consíguelos activando un Plan Premium
Comunidad
Pide ayuda a la comunidad y resuelve tus dudas de estudio
Ebooks gratuitos
Descarga nuestras guías gratuitas sobre técnicas de estudio, métodos para controlar la ansiedad y consejos para la tesis preparadas por los tutores de Docsity
Asignatura: Programming Methodology, Profesor: , Carrera: Ingeniería Informática, Universidad: UDIMA
Tipo: Apuntes
1 / 76
Esta página no es visible en la vista previa
¡No te pierdas las partes importantes!





































































A lo largo de la asignatura se ha estado utilizando el lenguaje algorítmico para describir algoritmos. Este lenguaje es fácilmente comprensible para nosotros, pero no por el ordenador.
Con el fin de poder ejecutar los algoritmos en el ordenador, se tendrán que des- cribir en un lenguaje que éste pueda entender. En este módulo veremos como codificar algoritmos en lenguaje C. De hecho, si hablamos con propiedad, el ordenador todavía no puede entender los programas codificados en lenguaje C. Es necesario todo un proceso de compilación y enlazado con el fin de traducir los programas escritos en C a un lenguaje que el ordenador sea capaz de ejecu- tar. Si se dispone de las herramientas adecuadas, sin embargo, este proceso es automático y no requiere intervención, por lo que, a efectos de la asignatura, se puede considerar que el lenguaje C es comprendido por el ordenador.
Hablando del lenguaje C, se puede decir que es un lenguaje de alto nivel, impe- rativo y estructurado, eficiente en la ejecución de los programas y muy utilizado, especialmente en la ingeniería y los campos científicos. Claro está que hay otros lenguajes de alto nivel igualmente válidos y con una estructuración mayor, o incluso orientados a objetos. Sería el caso del propio C++, para citar a uno. El lenguaje C, sin embargo, tiene el inestimable valor añadido de ser un lenguaje sencillo, próximo al lenguaje algorítmico. Además, es fácil disponer de excelen- tes compiladores de C gratuitos, para casi cualquier plataforma sobre la que se quiera trabajar y con entornos de programación claros y funcionales.
Este módulo didáctico, de todas maneras, no pretende en ningún caso ser ni un manual, ni tampoco una guía de referencia del lenguaje C. Al contra- rio, el enfoque del módulo se dirige a cubrir sólo aquella pequeña parte del C necesaria para poder codificar la notación algorítmica vista a la asignatu- ra.
En este sentido, la organización del presente módulo refleja la de los mó- dulos didácticos anteriores de la asignatura. Así, el estudio de cada uno de los diferentes apartados de este módulo se hará a continuación de la lectu- ra del módulo didáctico homónimo de la asignatura. Por lo tanto, el presen- te módulo se irá estudiando en paralelo con el del resto de módulos, y el conocimiento del lenguaje C se irá completando a medida que se completa también el conocimiento del lenguaje algorítmico.
El entorno de programación en lenguaje C se trata en el "Anexo de software" de la asignatura.
En otras asignaturas a lo largo de la carrera se completará el conocimiento del lenguaje C.
En este primer apartado veremos la estructura básica de un programa descrito en lenguaje C. no entraremos todavía en detalles sobre la traducción de la nota- ción algorítmica a lenguaje C.
1.1. Nuestro primer programa en C
Nuestro primer programa en lenguaje C será un breve pero emotivo saludo uni- versal. El programa podría ser similar a:
/* Programa hola.c - Saludo universal Jordi Riera, 2001 / #include <stdio.h> #include <stdlib.h> int main() { printf("Hola mundo!\n"); / Escribe "Hola mundo!" por pantalla / system("PAUSE"); / El programa espera una tecla */ return 0; }
Este sencillo trozo de código nos sirve para ilustrar algunas características im- portantes del lenguaje C, que comentaremos acto seguido.
La primera línea del programa es un comentario. En C, los comentarios están delimitados entre los caracteres "/" y "/". Tal como se ve en el ejemplo, pueden ocupar varios líneas. Evidentemente, los comentarios son siempre opcionales, pero recordad que un programa bien documentado será mucho más inteligible. Usaremos el primer comentario para indicar el nombre del programa, una breve descripción de lo que hace, al autor, etc.
En nuestro programa de saludo, después del comentario inicial, nos encontra- mos dos líneas que incluyen dos ficheros de declaraciones estándares del len- guaje C. Estos ficheros de declaraciones se llaman ficheros de cabecera o fiche- ros de include. Son proporcionados por el fabricante del compilador y contienen declaraciones de funciones, variables y constantes que el programador puede usar a partir de la inclusión del fichero con la directiva #include. El fichero stdio.h contiene, entre de otros, la declaración de la función printf que utilizare- mos más tarde. y el fichero stdlib.h la declaración de la función system.
Acto seguido viene el programa principal. Los programas en C siempre tienen que declarar la función main , que lo primero que se ejecutará y que, opcional- mente, podrá llamar a otras funciones declaradas. La función main retorna un
Ved el módulo "Introducción a la programación" si tenéis dudas sobre alguno de los conceptos usados en este apartado.
Podéis probar el programa usando el entorno de progra- mación. Consultad el "Anexo del software" para conocer los detalles.
Algunos entornos de progra- mación que trabajan en C++ y C aceptan comentarios de una sola línea delimitados por los caracteres "//" y el final de la línea. Pero eso no es C es- tándar.
Las directivas se han de escribir siempre…
... en la primera posición de una línea, ya que sino el com- pilador no las reconocería. Todas las directivas empiezan siempre por "#".
entero, por convenio un 0 para denotar una finalización correcta, y no necesita parámetros.
El cuerpo de la función está delimitado por los caracteres "{" y "}" que llamare- mos llaves. ¡En él encontramos una sentencia printf que imprime "Hola mundo!" por pantalla, una llamada al sistema operativo para que el programa espere una tecla, y una sentencia return que sale de la función main y acaba la ejecución del programa.
El código del programa de saludo universal muestra todavía una importante característica más del lenguaje C:
El lenguaje C distingue entre mayúsculas y minúsculas.
Así, tenemos que utilizar la función printf para escribir por pantalla. No podemos utilizar ni la función PRINTF , ni la Printf , ni la printF , que no estén declaradas en el fichero stdio.h. De la misma manera, tenemos que ir con cuidado con el uso del nombre correcto de todo objeto declarado en el programa.
1.2. Un programa más completo en lenguaje C
Acto seguido se muestra la traducción a lenguaje C del algoritmo media expre- sado en lenguaje algorítmico en el apartado 1.2 del módulo "Introducción a la programación". El algoritmo calcula la media de cuatro números:
/* Programa mediana.c - Media de cuatro números Jordi Riera, 2001 / #include <stdio.h> #include <stdlib.h> int main() { / Declaración de variables / int n, suma, y; float resultado; suma = 0; i = 1; while (i<=4) { scanf("%d", &n); / Lee un numero decimal por el teclado / suma = suma + n; /Acumula la suma de los números leídos / y = y + 1; } resultada = (float) suma / 4.0; printf( "%f", resultado); / Imprime la media por pantalla / system("PAUSE"); / Hacemos que el programa espere una tecla */ return 0; }
No os preocupéis por el funcionamiento del algoritmo o por los detalles de cómo se ha hecho la traducción. Todos estos aspectos quedarán mucho más claros
Las llaves "{" y "}" sirven para delimitar un bloque de código.
En este apartado se verán los objetos elementales, así como las estructuras algorítmicas, acciones y funciones del lenguaje C, necesarias para traducir a programas en C los algoritmos del módulo "Introducción al algorítmica".
2.1. Objetos elementales del lenguaje C
Tal como habéis visto en el lenguaje algorítmico, un objeto tiene tres atributos: nombre o identificador, tipo y valor. Los nombres o identificadores de los objetos siguen las mismas normas que en el lenguaje algorítmico: tienen que empezar por una letra, y después pueden seguir letras, números o el carácter "_". Tam- poco puede utilizar ninguna palabra reservada del lenguaje C (como while ) para identificar un objeto. La tabla siguiente contiene nombres correctos, incorrectos y un breve comentario.
Nombre o identifi- cador
¿Es correc- to? Comentario ventas Si Es recomendable escribir en minúsculas. _articulo No No empieza por un carácter alfabético. aux2 Si Poco recomendable. Es mejor usar nombres descrip-tivos. 1_articulo No No empieza por un carácter alfabético. numero articulos No Los espacios en blanco no son permitidos. numeroArticulos Si Es un nombre descriptivo.
piezaCamión No
No se pueden utilizar caracteres especiales ni acen- tos (la "ñ" se considera un carácter especial, recordad que los ordenadores provienen del mundo anglosa- jón). const No Es una palabra reservada del lenguaje C.
A continuación vamos a ver la traducción de los tipos elementales del lenguaje algorítmico al lenguaje C, así como los valores que éstos pueden tomar.
2.1.1. Tipos elementales en C
El lenguaje algorítmico define cuatro tipos elementales: booleano, entero, carac- ter y real. Acto seguido veremos cómo se traducen al lenguaje C.
Tipo booleano
El tipo booleano no existe como tal en el lenguaje C, pero lo podemos definir fácilmente usando la declaración siguiente:
typedef enum {FALSE, TRUE} bool;
A partir de este momento podemos utilizar el nuevo tipo bool para declarar obje- tos de tipo booleano.
La siguiente tabla resume las características del tipo booleano y su traducción a lenguaje C.
Característica Lenguaje algorítmico Lenguaje C Identificador booleano bool Rango de valores cierto, falso TRUE, FALSE Operadores inter- nos no, y, o, =,^ ≠, <,^ ≤, >,^ ≥^
!, &&, ||, ==, !=, <, <=,>, >=
Tipo caracter
En C los caracteres van delimitados por comillas simples como en el lenguaje algorítmico. La tabla siguiente resume las características del tipo carácter y su traducción a C.
Característica Lenguaje algorítmico Lenguaje C Identificador caracter char Rango de valores conjunto finito de valores conjunto finito de valoresdefinidos por el código ASCII Operadores exter- nos =,^ ≠, <,^ ≤, >,^ ≥^ ==, !=, <, <=, >, >= Sintaxis de valores 'a', 'W', '1' 'a', 'W', '1'
Hay que ir con cuidado porque el orden de los elementos (FALSE y TRUE) es importante, como veremos más adelante.
Para declarar una constante, se utiliza la construcción:
const tipo nombre = valor;
Notad que la palabra reservada const es obligatoria ante cada declaración de constante. No sirve para definir todo un bloque de declaraciones de constantes como en el lenguaje algorítmico, sino sólo para declarar una.
Este tipo de constante es conocida en tiempo de ejecución. Es decir, la asigna- ción del valor a la constante nombre se ganará durante la ejecución del progra- ma, y no durante la compilación.
A veces es conveniente definir constantes con valor conocido ya durante la compilación. Se puede hacer con la directiva #define :
#define NOMBRE valor
Observamos que no se indica el tipo de la constante que se está definiendo. De hecho, el compilador únicamente sustituye el nombre por su valor cada vez que lo encuentra en el código posterior a la declaración. Asimismo, es habitual usar un nombre escrito todo en mayúsculas al declarar una constante. De esta mane- ra el código del programa es más legible, ya que se pueden distinguir las cons- tantes de las variables con un solo vistazo.
Para declarar una variable, se usa la sintaxis siguiente:
tipo nombre;
Así se declara una variable de tipo tipo y nombre nombre. También se pueden declarar diversas variables del mismo tipo en una sola declaración, separando sus nombres por comas (","). Por ejemplo, para declarar tres variables i, j , k de tipo entero:
int i, j, k;
Finalmente, remarcar que aunque el lenguaje C no usa palabras reservadas para delimitar las declaraciones de variables y constantes, nosotros colocare- mos los comentarios apropiados para hacer el programa más legible.
Las constantes conocidas en tiempo de compilación serán útiles para la parametrización de tipos de datos estructura- dos, como las tablas. Se co- mentarán en el apartado 4.1.4. "Acceso directo a una tabla" del presente módulo.
El lenguaje C… ... permite indicar un valor inicial por la variable en la propia declaración, pero evita- remos esta construcción que no es permitida en el lenguaje algorítmico.
2.1.3. Expresiones en C
Las expresiones en lenguaje C siguen las mismas reglas de construcción y eva- luación que en el lenguaje algorítmico. En caso de duda, sin embargo, siempre es aconsejable poner un paréntesis de más para indicar claramente la orden de evaluación de la expresión.
2.1.4. Definición de tipos. Tipos enumerados en C
Tal como sucede con las declaraciones de variables y constantes, las declara- ciones de tipo en C tampoco van delimitadas por palabras reservadas. Se tienen que colocar entre las declaraciones de las constantes y las de las variables, indicando con un comentario que se procede a hacer declaraciones de tipo.
El constructor de tipos enumerados en C sigue la siguiente sintaxis:
typedef enum {valor 1 , valor (^) 2. .., valor (^) n } nombre;
Como en el lenguaje algorítmico, el orden en que se enumeran los valores sirve para establecer las relaciones más pequeño a más grande y por lo tanto la or- den en que se enumeran los valores es importante. En C se puede asignar un entero a cada valor, para establecer estas relaciones, pero nosotros no utiliza- remos esta característica.
Recordad que hemos visto un ejemplo de esta sintaxis en la definición del tipo booleano.
2.3.1. Estructura general de un programa en lenguaje C
La estructura de un programa en lenguaje C es la siguiente:
/* Programa estructura.c - Estructura básica de un programa en C Jordi Riera, 2001 / / Inclusión de ficheros de cabecera / #include <fichero 1 > #include <fichero 2 > ... / Declaración de constantes en tiempo de compilación / #define NOMBRE_DEFINE1 valor_define #define NOMBRE_DEFINE2 valor_define ... / Declaración de tipos / typedef enum {FALSE, TRUE} bool; / tipo booleano / typedef definicion_de_tipo1 nombre_tipo 1 ; typedef definicion_de_tipo2 nombre_tipo 2 ; … int main() { / Definición de constantes / cons t tipo_de_constante1 nombre_constante1 = valor_constante1; cons t tipo_de_constante2 nombre_constante2 = valor_constante2; ... / Declaración de variables */ tipo_de_variable1 nombre_variable1; tipo_de_variable2 nombre_variable2;
/* Cuerpo del programa */ acción acción ... }
Observad que las declaraciones de tipos se han hecho fuera de la función main del programa. Eso es porque habitualmente es deseable que los tipos de datos estén disponibles en todo el programa y para todas las funciones que en él se puedan declarar. De todas maneras, también se pueden hacer declaraciones de tipo locales, situándolas entre las declaraciones de las constantes y las de las variables.
2.3.2. Acciones elementales: la asignación
La acción de asignación del lenguaje algorítmico, ":=" se traduce en el operador de asignación en lenguaje C, "=". La distinción entre acción y operador es muy importante, ya que implica que el lenguaje C permite hacer asignaciones en cualquier punto del código donde una expresión sea válida. Por ejemplo, es un error muy común hacer una asignación, en vez de una comparación en la condi- ción de una sentencia condicional, por usar el operador de asignación "=" en lugar del operador relacional de igualdad "==", lo cual tiene graves repercusio- nes de cara al buen funcionamiento del programa.
2.3.3. Composición de acciones
Veremos ahora como combinar acciones elementales para poder construir pro- gramas más complejos.
Composición secuencial
En C, la composición secuencial se hace como en el lenguaje algorítmico, escri- biendo una acción a continuación de la otra y separando cada acción de la si- guiente con un ";".
Si queréis agrupar un conjunto de acciones en un bloque, las podéis colocar entre las llaves "{" y "}".
Composición alternativa
La sintaxis de la composición alternativa de acciones en lenguaje C es la si- guiente:
if ( expresión ) { acciónA } else { acciónB }
Notad que el paréntesis entorno a la expresión es obligatorio y forma parte de la sintaxis. Las acciones a ejecutar condicionalmente ( acciónA y acciónB) son bloques de acciones delimitados por llaves (composición secuencial). Si sólo hubiera que ejecutar una acción simple, se podrían eliminar las llaves corres- pondientes.
Es recomendable utilizar si- empre las llaves, aunque sólo haya que colocar una acción. ¡Quizás más adelante habrá que añadir otras nuevas!
Usando la construcción for se puede codificar el programa que calcula el facto- rial de un número entero.
/* Programa fact.c - Calcula el factorial de n Jordi Riera, 2001 / #include <stdio.h> #include <stdlib.h> int main() { / Declaración de variables / int i, n, fact; scanf("%d", &n); / Leemos uno numero entero por teclado / / Pre: n=N y N>=0 y N<=16 / fact = 1; for (i=1; i<=n; i++) { fact = fact * i; } / Post: fact es el factorial de N / printf("%d\n", fact); / Escribimos el resultado por pantalla / system("PAUSE"); / Hacemos que el programa espere una tecla */ return 0; }
Observad que hemos añadido una nueva condición en la precondición, concre- tamente N<=16. Esta condición no viene impuesta por una limitación del algo- ritmo, sino por su codificación en un programa en C. La limitación está en el entero mayor que se puede representar en el ordenador. Observad qué pasa si introducís por teclado el número 17, por ejemplo.
2.4. Acciones y funciones en C
El lenguaje C no dispone de acciones en el sentido de la notación algorítmica. En C, todo son funciones. Recordad que incluso el algoritmo principal se escribe dentro de la función main.
De todas maneras, en lenguaje C también se puede distinguir entre acciones y funciones. Se hará según la manera de declarar parámetros y la forma de hacer las invocaciones. En una función sólo se declararán parámetros de entrada, y se invocará dentro de una expresión. En una acción se podrán declararán paráme- tros de todo tipo, y se invocará allí donde una acción sea válida.
Considerando estas restricciones, la sintaxis para la declaración de una acción en C es:
void nombre (param 1 , param2. .., paramn ) { ... cuerpo de la acción }
Teneis otra solución al algoritmo fact, usando while en lugar de for, en el apartado 3.3.3. “Composición iterativa”, del módulo “Introducción a la algorítmica” de la asignatura.
Para una definición precisa de lo que son las acciones y las funciones, consultad el apar- tado 4. “Acciones y funciones” del módulo “Introducción a la algorítmica” de la asignatura.
void... ... es un tipo especial del len- guaje C que indica que la fun- ción no devuelve ningún valor.
Y la correspondiente invocación de la acción es:
nombre ( obj 1 , obj2. .., obj n );
En el caso de una función, la sintaxis para su declaración en C es:
tipo nombre (param 1 , param2. .., paramn ) { ... cuerpo de la función return expresión; }
Y la correspondiente invocación de la función es:
nombre ( obj 1 , obj2. .., obj (^) n )
Tal como sucede en el lenguaje algorítmico, las acciones y funciones en C pue- den declarar su entorno local, con definiciones de constantes, tipo y variables propias. La sintaxis es la misma que se ha utilizado en la función main.
También, al igual que las variables, en C hay que declarar las acciones y fun- ciones antes de su uso. Una práctica muy conveniente es predeclarar todas las funciones y acciones al principio del fichero (después de los includes, defines y typedefs) con lo cual podemos declararlas después allí dónde queramos y nos podremos despreocupar a la hora de utilizarlas de si ya las hemos declarado o no.
La predeclaración de la acción/función es muy parecida a la primera línea de la declaración, sin embargo, en lugar de los parámetros se pueden poner sólo sus tipos:
tipo nombre(tipus 1 , tipus (^) 2. .., tipo (^) _n); / función / void nombre2(tipus 1 , tipus_ (^) 2. .., tipo (^) _n); / acción /_
Igualmente es más recomendable, por claridad, poner todo el parámetro como en la declaración:
La invocación sólo será válida dentro de una expresión don- de se espera un valor del tipo que devuelve la función.