SlideShare una empresa de Scribd logo
1 de 27
Descargar para leer sin conexión
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
1
Introducción a ANSI C y Visual C++
El propósito de este boletín de prácticas es servir como material de apoyo y consulta para los
aspectos esenciales de C que se utilizarán en MTP. También se ha incluido una breve
introducción al uso de Visual C++ y en particular a su depurador (debugger).
Introducción a ANSI C
1 Aspectos básicos de C
Todo programa en C tiene una función principal por la que comienza la ejecución (main).
1.1 Declaración de variables
Tipos Básicos
• char, un carácter, visto también como valores enteros desde -128 a 127.
• int, entero, valor desde -32768 a 32767.
• long, entero largo, valor desde -215
a 215
-1.
• float, coma flotante simple precisión, con decimales.
• double, coma flotante doble precisión.
Para definir variables locales a una función, después de la llave que abre una función especificar
el tipo seguido de una lista de variables separada por comas, y finalizada con “;” .
/* Este es mi primer programa en C */
#include<stdio.h>
main()
{
printf(“Hola mundon”);
}
Comentarios
Inclusión de la definición
de funciones de librería
Función principal
Código del programa
main() {
int i,j,k;
char tecla;
...
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
2
Tipos Estructurados
• Arrays n-dimensionales:
char nombre[50];
float matriz[20][20];
para acceder a los elementos de los array:
c=nombre[0];
matriz[5][2]=2.5;
• Registros
struct persona{
int edad;
int peso;
char nombre[40];
} director, recepcionista, vendedores[20];
Para acceder a los campos de un registro hay que usar el operador punto ‘.’:
director.edad=40;
recepcionista.peso=80;
vendedores[5].nombre[2]=‘p’;
Se pueden definir tipos para usarlos en muchos lugares, con la palabra reservada typedef:
typedef struct
{
double real, imaginary;
} complex;
Las estructuras pueden ser asignadas, pasadas a funciones y devueltas por las mismas, pero no
pueden ser comparadas, por lo que:
complex a, b;
a.real=0; a.imaginary=0;
b=a;
es correcto, pero lo que sigue no lo es y debe hacerse campo a campo.
if(a==b)
Esto es un string
Ojo, siempre empiezan
por 0
Nombre identificador del struct
Campos
Variables de tipo registro persona
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
3
Constructores Estructurados
1. Selección
if(i==3) /* para la desigualdad usar != */
j=4;
else{ /* las llaves son necesarias si hay más de una sentencia */
j=5; k=6;
}
switch(i){ /* la expresión se evalúa a entero o carácter */
case 1: printf(“i vale uno”);
break;
case 2: printf(“i vale dos”);
break;
default: printf(“i no vale ni uno ni dos”);
}
2. Bucles
while(i<30){ /* test al principio del bucle */
hacer_cosas(i);
i=i+1; /* también se puede usar i++ */
}
do{
hacer_cosas(i); /* el código se ejecuta al menos una vez */
i=i+1;
}while(i<30); /* test al final del bucle */
for(n=0; n<200; n++){ /*for(inicialización;test;actualización)*/
hacer_cosas(i);
}
for(i=3;i<5;i=i+1){
hacer_cosas(i);
}
i=3;
while (i<5){
hacer_cosas(i);
i=i+1;
end;
equivalencia
entre el for
y el while
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
4
Se puede modificar el comportamiento de los bucles ejecutando las sentencias:
continue, que interrumpe el ciclo actual y va al siguiente ciclo, y
break, que interrumpe el bucle.
Por ejemplo: el siguiente bucle sólo ejecuta la sentencia printf cuando la variable i toma los
valores 0 y 2.
1.2 Punteros
Dado un tipo T, T* es el tipo “puntero a T”. Es decir, una variable de tipo T* puede contener la
dirección de un objeto de tipo T.
char *strp; /* strp es un puntero a char */
char car=`a`; /* car es un char */
strp=&car; strp: &car
car: a
car=*strp;
strp=car; /* error*/
1.3 Entrada/Salida
La definición estándar de C no incluye sentencias para la E/S de información. C tiene definidas
las funciones de E/S en bibliotecas de funciones aparte. Para poder usarlas se deben incluir las
definiciones de las funciones (stdio.h) en nuestros programas mediante la directiva
#include< >
Entrada
scanf es una función de entrada de datos, según el formato definido en el string del primer
argumento, que guarda la información introducida en las variables colocadas en el resto de los
argumentos.
Algunos formatos reconocidos:
%c char %s string
%d int %ld long
%f float
...
i=0;
while(i<5){
if(i==1){
i=i+1;
continue;
}
if(i==3)
break;
printf(“i = %dn”, i);
i++;
}
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
5
Para indicar las variables en las que se desea que se guarde la información se deben pasar
punteros a ellas. Para ello basta con anteponer el símbolo & al nombre de la variables, excepto
en el caso de los strings.
Ejemplos:
scanf(“%d”, &i);
scanf(“%d”, &director.edad);
scanf(“%s”, vendedor[i].nombre);
scanf(“%f%f”, &a.real, &a.imaginary);
scanf(“%f”, &matriz[i][j]);
no hace falta el & por
ser un string
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
6
Salida
printf es una función de salida de información. Su primer argumento es un string con el
formato que debe tener la información que se muestre. Los siguientes argumentos son las
variables que contienen la información que se quiere mostrar.
Los formatos reconocidos son los mismos que acepta la función scanf.
Se pueden emplear algunos caracteres especiales como:
n Imprime un salto de línea.
t Imprime un tabulador.
 Imprime la barra invertida.
Ejemplos:
printf(“La edad del director es %dn”, director.edad);
printf(“Vendedor: %dntNombre: %sntEdad: %dntPeso: %dn”, i,
vendedor[i].nombre, vendedor[i].edad, vendedor[i].peso);
1.4 Ejercicios propuestos
a. Escribir un programa que calcule el máximo, mínimo y la media de una lista indefinida de
números enteros positivos. En el caso de introducir un número negativo, dicho número debe
ser rechazado indicando el motivo. Un cero indicará que la lista de números se ha acabado.
b. Escribir un programa que lea un vector de cinco cifras y compruebe si es capicúa.
c. Escribir un programa que muestre por pantalla las tablas de multiplicar y dividir que el
usuario quiera, y finalice cuando el usuario indique que desea ver la tabla del cero.
d. Escribir un programa que lea una matriz cuadrada de enteros y escriba la diagonal inversa.
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
7
2 Funciones en C
C no tiene procedimientos, sólo funciones. Sus definiciones no pueden ser anidadas pero todas
excepto main pueden ser llamadas recursivamente.
2.1 Declaración de funciones
<tipo_retorno><nombre_función>(<lista_declaración _parámetros formales>);
Ejemplos de funciones en C:
• void dibujar(void); //sin argumentos y
//sin valor de retorno
• int dibujar(void); //sin argumentos y
//devuelve un int
• int calcula_producto(int x, int y);
// con argumentos de
// tipo int y devuelve int
En un fichero de código C las funciones deben declararse o definirse antes de ser utilizadas. En
el primer caso basta con hacer la declaración al principio del fichero, así ya no importará el
orden de definición de las funciones. En el segundo caso, se evita hacer las declaraciones pero
se debe poner atención al orden de definición de las funciones para que siempre la definición
sea anterior a su utilización, lo cual resulta incómodo cuando se trabaja con muchas funciones
en un fichero.
Como veremos más adelante, cuando las funciones están definidas en un fichero distinto al cual
donde se utilizan, necesariamente debe hacerse una declaración de dichas funciones.
2.2 Implementación de funciones en C
Cada función llamada en un programa debe estar implementada en algún sitio (y sólo una vez).
La sintaxis es:
<tipo_retorno><nombre_función>(<lista_declaración _parámetros formales>)
{
<variables locales>
<cuerpo>
}
Ejemplo de implementación de funciones en C:
int calcula_producto(int x,int y){
int rdo;
rdo=x*y;
return rdo;
}
Una función equivalente sería:
int calcula_producto(int x,int y)
{return x*y;}
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
8
2.3 Invocación de funciones en C
La invocación a una función se hace poniendo el identificador seguido de paréntesis
(obligatorios aunque no tenga parámetros) dentro de los cuales pondremos los parámetros. Los
parámetros deben ser del mismo tipo que el prototipo y la definición.
Ejemplo:
...
int a,b,rdo; a=5; b=7;
rdo=calcula_producto(a,b);
...
2.4 Retorno de valores en C
La sentencia de retorno es necesaria para poder devolver valores desde funciones. Su sintaxis
es:
return expresion;
2.5 Parámetros por valor y por referencia
Por defecto, los parámetros en C se pasan por valor.
Ejemplo: Una función para intercambiar el valor de dos variables:
void intercambio(int a,int b){
int temp=a;
a=b;
b=temp;
}
void main(){
int a=10,b=20;
intercambio(a,b);
}
Para pasar parámetros por referencia se utilizan punteros y lo que se pasa a la función es un
puntero a los parámetros cuyo contenido se desea modificar.
void intercambio(int *a,int *b){ (1)
int temp=*a; (2)
*a=*b;
*b=temp;
}
void main(){
int a=10,b=20;
intercambio(&a,&b); (3)
}
(1) int *a indica que la variable a es un puntero a entero (contiene la dirección de una
variable entera).
(2) el operador “*” referencia al puntero. *p es la variable entera apuntada por p.
¿Se intercambian los
valores de a y b?
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
9
(3) en la llamada se pasan referencias a variables enteras utilizando el operador “&”.
¿Se cambian los valores de a y b?. Véamos cuál sería la ejecución de la llamada.
a) int a=10,b=20;
b) intercambio(&a,&b);
// como primer parámetro se pasa la
// dirección de a y como segundo parámetro
// la dirección de b
c) int temp=*a; // temp=10;
d) *a=*b;
e) *b=temp;
2.6 Ejercicio Propuesto
Haga un programa que contenga tres funciones: una función lee el número, otra calcula el
cuadrado y otra visualiza el resultado. En pantalla debería aparecer algo así:
Dame un número: 5
5*5=25
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
10
3 Trabajando con funciones y variables en distintos ficheros
El diseño de un sistema, en nuestro caso representado básicamente por el diagrama de
estructura, debe implementarse físicamente en 1 o más ficheros de código fuente. Para la
mayoría de los sistemas, es inviable programarlos, probarlos y mantenerlos considerando como
único componente un fichero con todo código fuente. Tampoco resulta práctico utilizar para
cada módulo un fichero de código fuente. Con lo cual la decisión normalmente considera el
codificar varios módulos en un mismo fichero. El criterio de agrupación debe incluir aspectos
tales como: dependencia entre módulos (por invocaciones entre ellos o porque comparten
información), despliegue de los módulos en los mismos nodos (cuando el sistema es
distribuido), etc.
En C tenemos dos formas básicas de trabajar con varios ficheros en una aplicación: incluyendo
un fichero en otro mediante directivas del compilador (#include) o mediante la declaración de
funciones o variables extern.
3.1 Inclusión de ficheros en C
Cuando el preprocesador encuentra una directiva #include entonces busca el archivo
especificado en la instrucción y lo incluye en el fichero actual. La directiva #include en el
archivo de código fuente se sustituye por el texto del archivo incluido. La operación equivale a
que el usuario teclee toda la información que éste contiene. El nombre del archivo puede venir
de dos formas:
#include <stdio.h> // busca en directorios estándar del sistema
#include "mifichero.h" // busca en el directorio en el que se esté
// trabajando
¿Por qué incluir en un fichero otro fichero?
Los ficheros de encabezamiento (o cabeceras), contienen entre otras cosas:
• Constantes explícitas.
• Declaraciones de funciones.
• Declaraciones de tipos.
Ejemplo
Supongamos que se desea utilizar valores booleanos, es decir, queremos emplear CIERTO y
FALSO en lugar de 1 y 0, respectivamente. Podríamos crear un fichero que se llamase, por
ejemplo, "bool.h", que contuviera estas definiciones:
#define BOOL int
#define CIERTO 1
#define FALSO 0
Para poder utilizar CIERTO y FALSO incluiremos el fichero bool.h en donde se quisieran
utilizar.
#include "bool.h"
int main(void){
BOOL v1;
v1=CIERTO;
v1=FALSO;}
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
11
3.2 Declaraciones Extern
Las funciones y las variables definidas en ficheros pueden ser accedidas desde otros ficheros
donde deberían ser declaradas usando la palabra reservada "extern". En el caso de las
variables es obligatorio explicitar si son o no extern. En el caso de las funciones no es
necesaria su colocación, ya que por defecto las funciones son extern, sin embargo debe
siempre declararse el prototipo de estas funciones en el fichero donde serán utilizadas y antes de
hacer referencia a ellas.
3.3 Ejercicio
Resuelva los ejercicios a, b y c propuestos en la sección 1, pero implementando cada función en
un fichero distinto (main es también una función).
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
12
4 Manejo de archivos en C
Este capítulo es una breve introducción al manejo de archivos en C. Se describen solamente las
operaciones básicas: apertura, lectura, escritura y cierre de archivos. Lo suficiente para poder
manejar archivos binarios mediante acceso secuencial.
Las funciones de manejo de archivos están definidas en la librería stdio.h, por lo que para
poder utilizar archivos en un programa C debe incluirse dicha librería:
# include <stdio.h>
4.1 Declaración de archivos
En C se define un manejador del archivo, en forma de puntero al tipo FILE:
FILE *fich; /* fich es un manejador de Archivo */
Ligado a cada manejador existe un indicador de posición actual asociado al archivo. Este
indicador se actualiza en cada operación de lectura o escritura. Por ejemplo, después de leer un
bloque de datos el indicador apuntará a la siguiente posición en el archivo, a partir de donde se
seguirán leyendo datos.
4.2 Apertura de archivos
Para abrir un archivo existente o para crear un nuevo archivo se utiliza la función fopen cuya
cabecera es:
FILE *fopen(const char *Nombre_archivo, const char *modo);
fopen devuelve un puntero que es el manejador del archivo. Si alguna operación no es posible
devuelve NULL (por ejemplo, si se intenta abrir un archivo que no existe). Sus parámetros son:
Nombre_archivo: es una cadena con el nombre del archivo.
Modo: es una cadena que indica,
el modo de apertura:
r abre un archivo existente sólo en modo lectura. El puntero se posiciona
al comienzo del archivo.
w crea el archivo para escritura, si el archivo ya existe lo sobreescribe. El
puntero se posiciona al comienzo del archivo.
a abre el archivo para escribir al final del mismo (append). Si no existe lo
crea. El puntero se posiciona al final del archivo.
r+ abre un archivo existente para actualización (lectura y escritura). El
puntero se posiciona al comienzo del archivo.
w+ crea un nuevo archivo para actualización, si ya existe lo sobreescribe. El
puntero se posiciona al comienzo del archivo.
a+ crea un nuevo archivo para actualización al final del archivo. Si no
existe lo crea. El puntero se posiciona al final del archivo.
El tipo de archivo:
b binario.
t texto.
Ejemplo:
fich = fopen(“FicheroB”, “rb”);
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
13
Abre el archivo binario “FicheroB” en modo lectura, si “FicheroB” no existe
devuelve NULL.
fich = fopen(“FicheroT”, “w+t”);
Crea el archivo de texto con nombre “FicheroT” para lectura y escritura. Si no puede
crear el archivo devuelve NULL.
4.3 Cierre de archivos
Para cerrar un archivo se utiliza la función fclose. Si se quiere cambiar el modo de apertura
de un archivo (p.e. pasar de escritura a lectura o viceversa) previamente debe cerrarse.
int fclose (FILE *fich);
fclose cierra todos los buffers asociados con el manejador de archivo fich y devuelve 0 si
se ha cerrado con éxito y EOF (end-of-file, final de fichero) si no.
Ejemplo:
fclose(fich); /* cierra el archivo apuntado por ‘fich’ */
4.4 Operación de Escritura:
Para realizar la escritura de un bloque de datos en un archivo se utiliza la función fwrite. Sólo
podrá llevarse a cabo la escritura si el archivo está abierto para escritura o para actualización.
size_t fwrite(void *ptr, size_t talla, size_t n,FILE *fich)
fwrite escribe n elementos de una talla fija desde la estructura apuntada por ptr en el
archivo fich. Devuelve el número de elementos almacenados. En caso de realizarse la
operación con éxito ese número coincide con n; en caso contrario, el valor será menor que n.
Ejemplo:
typedef struct {
int a;
char b;
} Registro;
main() {
FILE *fich;
Registro Reg;
if ((fich = fopen(“FicheroB”, “wb”))==NULL) {
printf(“Error: no pudo crearse el archivon”);
return 1;
}
Reg.a= 10;
Reg.b= ‘c’;
fwrite(&Reg,sizeof(Reg),1,fich);
fclose(fich);
}
Primero, crea el archivo para escritura. Si no puede, muestra un mensaje de error y finaliza. La
instrucción fwrite almacena en fich 1 elemento de tamaño sizeof(Reg) que está en la
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
14
variable Reg. La función sizeof devuelve el tamaño en bytes del elemento pasado como
argumento.
4.5 Operación de Lectura
Para realizar la lectura de un bloque de datos desde un archivo se utiliza la función fread. Sólo
puede llevarse a cabo la operación si el archivo está abierto para lectura o para actualización.
size_t fread(void *ptr, size_t talla, size_t n, FILE *fich)
fread lee un número n de elementos de una talla fija (expresada en bytes) desde un
archivo fich y los almacena en la dirección apuntada por ptr. Devuelve el número de
elementos leídos. En caso de alcanzar el final del archivo, devuelve el número de elementos
leídos que será menor que n (pudiendo ser 0). El tamaño de la memoria reservada apuntada por
ptr debe ser al menos de talla × n bytes. El indicador de posición del archivo apunta al
siguiente bloque de datos a leer. Así, lecturas sucesivas recorrerán el archivo secuencialmente.
Ejemplo:
main() {
FILE *fich;
Registro Reg;
if ((fich = fopen(“FicheroB”, “rb”))==NULL) {
printf(“Error: no pudo abrirse el archivon”);
return 1;
}
fread(&Reg, sizeof(Reg), 1, fich);
fclose(fich);
}
Primero, abre el archivo para lectura. Si no puede, muestra un mensaje de error y finaliza. La
instrucción fread lee, desde el archivo fich, 1 elemento de datos de tamaño
sizeof(Reg) y lo guarda en la variable Reg.
Tenga cuidado con el uso de punteros. Observe que el primer argumento de fread es un
puntero, por lo que en el ejemplo se pasa la dirección de Reg (es decir, &Reg). Si Reg se
hubiera declarado como un puntero a Registro entonces la instrucción sería:
Registro *Reg;
...
fread(Reg, sizeof(*Reg), 1, fich);
Con estas operaciones es suficiente para recorrer un archivo de forma secuencial y almacenar
información al final del archivo. Cualquier otra operación sobre archivos como borrado de
datos, ordenación, inserción en una posición intermedia, etc. requiere el uso de archivos
auxiliares en los cuales se almacena temporalmente la información. Existen otras funciones
como fseek (para situar el puntero al archivo en una posición determinada), rewind (que
sitúa el puntero al comienzo del archivo), ftell (que indica la posición del puntero) etc.
4.6 Búsqueda Secuencial
En algunos módulos de la aplicación se debe implementar un recorrido secuencial de un archivo
hasta encontrar un registro determinado. Es el caso de los módulos de verificación tales como
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
15
"Verificar Tarjeta Permitida”. Puede basarse en la siguiente plantilla para
implementar dichos módulos:
FUNCIÓN VALIDAR (campo_búsqueda) RETORNA válido
Entrada: campo_búsqueda, campo del registro por el cual buscar
Salida: válido= 1 (válido), 0 (no válido), -1 (no encontrado)
INICIO
ABRIR_ARCHIVO;
encontrado = FALSO;
final_de_archivo = LEER_DE_ARCHIVO (registro);
MIENTRAS (NO final_de_archivo) Y (NO Encontrado) HACER
SI (campo_búsqueda = registro.campo_búsqueda) ENTONCES
encontrado = CIERTO;
FIN_SI
final_de_archivo = LEER_DE_ARCHIVO (registro);
FIN_MIENTRAS;
CERRAR_ARCHIVO;
SI (NO Encontrado) RETORNAR -1;
SI (ES registro VÁLIDO) RETORNAR 1;
SI NO RETORNAR 0;
FIN
A continuación se muestra como ejemplo la implementación de una función que valida si
determinado campo de un registro cumple una condición. En concreto, si el campo “saldo”
de un registro del fichero “FcuentasB”, cuya clave de acceso es “n_cuenta”, es mayor que
1000.
int validar_saldo_mayor_1000 (Numero_Cuenta n_cuenta)
/* Entrada: n_cuenta número de cuenta a buscar
Salida: 1 si saldo > 1000; 0 si saldo <= 1000;
-1 si no puede abrir archivo
*/
{
FILE *FCuentas;
int encontrado = 0;
Reg_Cuenta rc;
if ((FCuentas=fopen("FcuentasB","rb"))==NULL) return -1;
else {
while (!encontrado && fread(&rc,sizeof(rc),1,FCuentas) )
/* el registro buscado es aquel tal que rc.n_cuenta=n_cuenta
la comparación debe hacerse campo a campo */
if (!strcmp(rc.n_cuenta.cod_banco,n_cuenta.cod_banco) &&
!strcmp(rc.n_cuenta.cod_sucursal,n_cuenta.cod_sucursal)
&&
!strcmp(rc.n_cuenta.cod_cuenta,n_cuenta.cod_cuenta))
encontrado=1;
fclose(FCuentas);
if (!encontrado) return -1;
/* a continuación se valida el registro */
if (rc.saldo > 1000) return 1;
else return 0;
}
}
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
16
4.7 Actualización de un registro
Los módulos que actualizan un almacen de datos deben buscar el registro a actualizar,
modificarlo y guardarlo en el almacen de datos. Es el caso de módulos como Actualizar
Saldo. Una posible plantilla para esos módulos sería:
FUNCIÓN ACTUALIZAR(campo_búsqueda, valor_actualización) RETORNA ok
Entrada: campo_búsqueda, campo del registro por el cual buscar
valor_actualización, valor a asignar al campo que se va a
actualizar
Salida: ok: 1 (éxito) 0 (no encontrado o problemas de archivo)
INICIO
ABRIR_ARCHIVO_COPIA; (para escritura)
ABRIR_ARCHIVO_ORIGEN; (para lectura)
final_de_archivo = LEER_DE_ARCHIVO_ORIGEN (registro);
MIENTRAS (NO final_de_archivo) HACER
SI (campo_búsqueda = registro.campo_búsqueda) ENTONCES
Registro.campo_a_actualizar=valor_actualización;
FIN_SI
ESCRIBIR_EN_ARCHIVO_COPIA (registro);
final_de_archivo = LEER_DE_ARCHIVO_ORIGEN (registro);
FIN_MIENTRAS;
CERRAR_ARCHIVO_ORIGEN;
CERRAR_ARCHIVO_COPIA;
ARCHIVO_ORIGEN = ARCHIVO_COPIA;
FIN
A continuación se muestra como ejemplo la implementación de una función que
actualiza un campo de un registro. En concreto, el campo “cantidad permitida” de
un registro del archivo “FtarjetasB” cuya clave de acceso es “n_tarjeta”.
int modificar_cantidad_permitida (Numero_Tarjeta n_tarjeta, float
cantidad)
/* Entrada: n_tarjeta, número de tarjeta a buscar
cantidad, valor de actualización del campo 'cantidad_permitida'
Salida: 1 si se ha actualizado con éxito,
0 si no (problemas con archivos, o no encuentra n_tarjeta)
*/
{
FILE *Fcopia, *Ftarjetas;
Reg_Tarjeta r;
int encontrado=0;
if ((Fcopia=fopen("Fcopia","wb"))==NULL) return 0;
if ((Ftarjetas=fopen("FtarjetasB","rb"))==NULL) return 0;
while (fread(&r,sizeof(r),1,Ftarjetas)) {
if (!strcmp(r.num_tarjeta.cod_banco,n_tarjeta.cod_banco) &&
!strcmp(r.num_tarjeta.cod_tarjeta,n_tarjeta.cod_tarjeta)){
encontrado=1;
r.cantidad_maxima=cantidad; /* se modifica el registro */
}
fwrite(&r,sizeof(r),1,Fcopia);
}
fclose(Ftarjetas);
fclose(Fcopia);
remove("FtarjetasB");
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
17
rename("Fcopia","FtarjetasB");
if (encontrado) return 1;
else return 0;
}
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
18
5 Manejo de cadenas en C
Para el manejo de cadenas (‘strings’) en C, este provee una librería <string.h>. En ésta se
definen varias funciones para manipular cadenas.
5.1 Definición de cadenas
Una cadena en C puede definirse como un vector de caracteres. Por ejemplo, en
char nombre[10];
se define la cadena nombre con un máximo de 10 caracteres, incluyendo el símbolo de fin de
cadena ‘0’.
Las operaciones básicas con cadenas son:
5.2 Copia de cadenas
char *strcpy(char *destino, const char *origen);
strcpy copia la cadena origen en la cadena destino hasta que encuentra la marca de
terminación ‘0’. Como valor de retorno devuelve la cadena origen.
Ejemplo:
main() {
char nombre1[10], nombre2[10];
strcpy(nombre1, “Juan”);
strcpy(nombre2, nombre1);
}
Tanto nombre1 como nombre2 contienen la cadena “Juan”.
char *strncpy(char *destino, const char *origen, size_t max);
strncpy copia la cadena origen en la cadena destino hasta un máximo de max caracteres o
hasta que encuentra la marca de terminación ‘0’. Como valor de retorno devuelve la cadena
origen.
5.3 Comparación de cadenas:
int strcmp(const char c1, const char c2)
strcmp compara las cadenas c1 y c2. Devuelve 0 si son iguales, un valor menor que 0 si c1
< c2 y un valor mayor que 0 si c1 > c2.
Ejemplo:
main() {
char nombre1[10], nombre2[10];
strcpy(nombre1, “Juan”);
strcpy(nombre2, “Luis”);
if (strcmp(nombre1,nombre2)==0) printf(“Iguales”);
else printf(“Distintos”);
}
int strncmp(const char c1, const char c2, size_t max)
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
19
strncmp compara las cadenas c1 y c2 hasta un máximo max de caracteres. Devuelve 0 si
son iguales, un valor menor que 0 si c1 < c2 y un valor mayor que 0 si c1 > c2.
5.4 Longitud de cadenas
size_t strlen(const char c)
strlen devuelve la longitud de la cadena c, sin contar el carácter de terminación de cadenas.
Ejemplo:
main() {
char nombre1[10];
strcpy(nombre1, “Juan”);
printf(“Longitud de nombre1 es %d”, strlen(nombre1));
}
5.5 Concatenar cadenas:
char strcat(const char destino, const char origen)
strcat concatena una copia de la cadena origen al final de la cadena destino. Añade el
carácter de terminación al final de la cadena destino. Devuelve la cadena concatenada.
Ejemplo:
main() {
char nombre1[10];
strcpy(nombre1, “Juan”);
strcat(nombre1,” Luis”);
/* nombre1 contiene “Juan Luis” */
}
char strncat(const char destino,const char origen,size_t max)
strncat concatena una copia de la cadena origen al final de la cadena destino hasta un
máximo de max caracteres. Añade el carácter de terminación al final de la cadena destino.
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
20
6 Variables Estáticas
Constituyen una clase de almacenamiento diferente a las variables automáticas y extern. Una
variable estática se especifica anteponiendo a la declaración normal la palabra static. Por
ejemplo, una variable de tipo int y estática se define como:
static int id;
Se definen locales a una función o a un fichero.
6.1 Variables estáticas locales a una función
En este caso, la variable estática se diferencia de la variable automática en que su existencia es
permanente, en lugar de aparecer y desaparecer cada vez que se activa la función.
En el siguiente ejemplo se utiliza una variable estática como buffer de una línea y un índice que
nos indica cuál fue el carácter accedido en la última invocación de la función.
int func(int x){
static int y; /* variable estática */
y++; /* el valor de la y se incrementa cada */
return (x+y); /* vez que se llama a la funcion */
}
6.2 Variables estáticas locales a un fichero
En este caso, la variable será accesible desde todas las funciones que se declaren dentro del
mismo fichero, y será invisible fuera del archivo en que está declarada. static tiene sentido
de permanencia y de privacidad. Veamos un ejemplo:
/* fichero1.c */
static int valor = 0;
int leer(void)
{
return(valor);
}
void escribir(int
nuevo_valor)
{
valor = nuevo_valor;
}
/* fichero2.c */
#include <stdio.h>
main()
{
int x, y;
x = leer();
x++;
escribir(x);
y = leer();
printf(“valor: %d”,y);
}
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
21
La representación del “cluster de información” del ejemplo es la siguiente:
Escribir
Leer
valor
nuevo_valor
valor
a2
a1
6.3 Ejercicio
Utilizando el ejemplo anterior, modificar las funciones para que se escriba y se lea una
estructura con un campo de tipo int y otro de tipo char.
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
22
Introducción a Visual C++
En esta sección se indican los pasos básicos para crear en Visual C++ un proyecto del tipo
aplicación de consola. También, estudiando un ejemplo, se incluye una breve presentación del
uso del depurador de Visual C++.
Para crear un nuevo proyecto se activa el menú File | New. En Projects se selecciona
Win32 Console Application y se da un nombre al proyecto (que será el nombre de la
carpeta donde se guardarán los fuentes, compilados y ejecutable) (ver Figura 1). Después se
escoge como tipo de proyecto Empty Project.
Figura 1: Creación de un nuevo proyecto
Para crear un nuevo archivo fuente se activa File | New, y posteriormente C++ source
file en Files. En el caso de que el fichero ya esté creado, y queramos añadirlo al proyecto,
se activa la opción Project | Add to project | Files (ver Figura 2). En nuestro caso
el fichero ya está creado, trabajaremos con el fichero calcularSumaOPromedioConMain.c.
El código del fichero se muestra a continuación:
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
23
#include <stdio.h>
int calcularSuma(int vectorEnteros[], int tamanyo) {
int i, suma = 0;
for (i = 0; i < tamanyo; i++) {
suma = suma + vectorEnteros[i];
}
return (suma);
}
int calcularPromedio(int vectorEnteros[], int tamanyo) {
int suma;
int media;
suma = calcularSuma(vectorEnteros, tamanyo);
media = suma / tamanyo;
return (media);
}
float calcularSumaOPromedio(int opcion, int vectorEnteros[], int tamanyo) {
float resultado = 0.0;
switch (opcion) {
case 1:
resultado = (float) calcularSuma(vectorEnteros, tamanyo);
break;
case 2:
resultado = (float) calcularPromedio(vectorEnteros, tamanyo);
break;
}
return (resultado);
}
void main() {
int vector[] = { 2, 2, 2, 4, 4, 4};
printf("%f",calcularSumaOPromedio(1,vector,6));
printf("%f",calcularSumaOPromedio(2,vector,6));
}
Una vez introducido el fichero, éste se ha compilar. Para ello se activa Build | Compile
(Ctrl + F7). Posteriormente se ha de enlazar, por lo que se elige Build | Build (F7).
Ahora ya se puede ejecutar el archivo a través de la opción Build | Execute (Ctrl +
F5). Los tres pasos se pueden hacer de una sola vez con esta última opción.
Tras ejecutar el proyecto se observa que éste se ejecuta sin problemas. Sin embargo, si se
sustituye en la función main las líneas
printf("%f",calcularSumaOPromedio(1,vector,6));
printf("%f",calcularSumaOPromedio(2,vector,6));
por estas otras:
printf("%f",calcularSumaOPromedio(1,vector,0));
printf("%f",calcularSumaOPromedio(2,vector,0));
y se repiten los tres últimos pasos (compilar, enlazar y ejecutar), la ejecución falla, mostrando
un mensaje de error (ver Figura 3).
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
24
Figura 2: Añadiendo un fichero al proyecto
Figura 3: Mensaje de error de ejecución
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
25
Para descubrir dónde se produce el error utilizaremos el debugger que incorpora Visual C++.
Lo primero que hay que establecer son los puntos de ruptura (breakpoints), que permiten
detener la ejecución del programa en una determinada línea. Para insertar un punto de ruptura
(que se identifica como un punto rojo), se selecciona la línea donde se quiere insertar, y
posteriormente con el botón derecho se invoca Insert/Remove Breakpoint. Para poder
ejecutar ahora el código, se selecciona la opción Build | Start Debug | Go (F5).
Aparece entonces una flecha amarilla que indica qué línea del código va a ser la siguiente en
ejecutarse. Para avanzar en la ejecución del programa se pulsan las teclas F11 (Step into),
que permite ver la ejecución paso a paso dentro de una función, o F10 (Step over), que
ejecuta de una vez el código de la función.
Insertar un punto de ruptura en la línea printf("%f",calcularSumaOPromedio(1,vector,0))
de la función main e iniciar el debugger (ver Figura 4).
Figura 4: Ejecución con el depurador
En la parte inferior de la pantalla pueden verse las variables del programa junto con los
diferentes valores que van tomando durante la ejecución. En cualquier momento se puede
abandonar el debugger con la opción Debug | Stop Debugging (Shift + F5).
Si se ejecuta paso a paso el fichero (con F10, F11) hasta llegar a la situación descrita en la
Figura 5, y se observa el valor de las variables, se comprueba que tanto suma como tamanyo
tienen el valor 0.
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
26
Figura 5: Paso previo a la instrucción de división por 0
Llegados a este punto, y tras pulsar de nuevo F11, se muestra un mensaje de error, y la
ejecución finaliza debido a la excepción producida al intentar realizar una división por 0 (ver
Figura 6). La solución a este problema consistiría en controlar el valor de la variable tamanyo
en las funciones que hacen uso de ella.
Metodología y Tecnología de la Programación
Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia.
27
Figura 6: Mensaje de error de ejecución estando en modo de depuración

Más contenido relacionado

Similar a Introduccion a C++.pdf

Similar a Introduccion a C++.pdf (20)

Elementos basicos c++
Elementos basicos c++Elementos basicos c++
Elementos basicos c++
 
Elementos basicos c++
Elementos basicos c++Elementos basicos c++
Elementos basicos c++
 
Lenguajecviviana
LenguajecvivianaLenguajecviviana
Lenguajecviviana
 
Tema vi guia de c
Tema vi guia de cTema vi guia de c
Tema vi guia de c
 
Repaso del lenguaje C++
Repaso del lenguaje C++Repaso del lenguaje C++
Repaso del lenguaje C++
 
Escuela
EscuelaEscuela
Escuela
 
Escuela
EscuelaEscuela
Escuela
 
Clase 1 Lenguaje C++
Clase 1 Lenguaje C++Clase 1 Lenguaje C++
Clase 1 Lenguaje C++
 
Ikgi
IkgiIkgi
Ikgi
 
C++.pdf
C++.pdfC++.pdf
C++.pdf
 
Instituto tecnológico particular
Instituto tecnológico particularInstituto tecnológico particular
Instituto tecnológico particular
 
Introduccion a c++
Introduccion a c++Introduccion a c++
Introduccion a c++
 
Sesion 4
Sesion 4Sesion 4
Sesion 4
 
Turbo c
Turbo cTurbo c
Turbo c
 
C++
C++C++
C++
 
Republica bolivariana de venezuela
Republica bolivariana de venezuelaRepublica bolivariana de venezuela
Republica bolivariana de venezuela
 
Estructura de Lenguaje C++
Estructura de Lenguaje C++Estructura de Lenguaje C++
Estructura de Lenguaje C++
 
Borland c
Borland  cBorland  c
Borland c
 
Lenguajec diapositivas
Lenguajec diapositivasLenguajec diapositivas
Lenguajec diapositivas
 
Lenguajec 1
Lenguajec 1Lenguajec 1
Lenguajec 1
 

Más de Daniel Carpio Contreras (13)

Teoria-Sistemas-Clases-09-10.ppt
Teoria-Sistemas-Clases-09-10.pptTeoria-Sistemas-Clases-09-10.ppt
Teoria-Sistemas-Clases-09-10.ppt
 
Teoria-Sistemas-Clases-01-06.ppt
Teoria-Sistemas-Clases-01-06.pptTeoria-Sistemas-Clases-01-06.ppt
Teoria-Sistemas-Clases-01-06.ppt
 
Teoria-Sistemas-Clases-15-16.ppt
Teoria-Sistemas-Clases-15-16.pptTeoria-Sistemas-Clases-15-16.ppt
Teoria-Sistemas-Clases-15-16.ppt
 
Teoria-Sistemas-Clases-13-14.ppt
Teoria-Sistemas-Clases-13-14.pptTeoria-Sistemas-Clases-13-14.ppt
Teoria-Sistemas-Clases-13-14.ppt
 
Teoria-Sistemas-Clases-07-08.ppt
Teoria-Sistemas-Clases-07-08.pptTeoria-Sistemas-Clases-07-08.ppt
Teoria-Sistemas-Clases-07-08.ppt
 
AudInf-COBIT.ppt
AudInf-COBIT.pptAudInf-COBIT.ppt
AudInf-COBIT.ppt
 
La+Teoria+General+de+Sistemas.doc
La+Teoria+General+de+Sistemas.docLa+Teoria+General+de+Sistemas.doc
La+Teoria+General+de+Sistemas.doc
 
Usando la Teoría de Control
Usando la Teoría de ControlUsando la Teoría de Control
Usando la Teoría de Control
 
Archivos.pdf
Archivos.pdfArchivos.pdf
Archivos.pdf
 
Manual de C++.pdf
Manual de C++.pdfManual de C++.pdf
Manual de C++.pdf
 
Introduccion.ppt
Introduccion.pptIntroduccion.ppt
Introduccion.ppt
 
Manejo_archivos.ppt
Manejo_archivos.pptManejo_archivos.ppt
Manejo_archivos.ppt
 
Programación C++.pdf
Programación C++.pdfProgramación C++.pdf
Programación C++.pdf
 

Último

04-circuitos-comparadores de amplificadores operacionales.pptx
04-circuitos-comparadores de amplificadores operacionales.pptx04-circuitos-comparadores de amplificadores operacionales.pptx
04-circuitos-comparadores de amplificadores operacionales.pptxHenryApaza12
 
SESIÓN 1 - Tema 1 - Conceptos Previos.pdf
SESIÓN 1 - Tema 1 - Conceptos Previos.pdfSESIÓN 1 - Tema 1 - Conceptos Previos.pdf
SESIÓN 1 - Tema 1 - Conceptos Previos.pdfElenaNagera
 
FOLIACIONES Y LINEACIONES GEOLOGÍA ESTRUCTURAL
FOLIACIONES Y LINEACIONES GEOLOGÍA ESTRUCTURALFOLIACIONES Y LINEACIONES GEOLOGÍA ESTRUCTURAL
FOLIACIONES Y LINEACIONES GEOLOGÍA ESTRUCTURALRiveraPemintelAlejan
 
movimiento circular univormemente variado
movimiento circular univormemente variadomovimiento circular univormemente variado
movimiento circular univormemente variadoEsthefaniaAuquilla1
 
Capacitación Anexo 6 D.s. 023 seguridad y salud ocupacional
Capacitación Anexo 6 D.s. 023 seguridad y salud ocupacionalCapacitación Anexo 6 D.s. 023 seguridad y salud ocupacional
Capacitación Anexo 6 D.s. 023 seguridad y salud ocupacionalamador030809
 
FOTOCELDAS Y LOS DIFERENTES TIPOS QUE EXISTEN.pdf
FOTOCELDAS Y LOS DIFERENTES TIPOS QUE EXISTEN.pdfFOTOCELDAS Y LOS DIFERENTES TIPOS QUE EXISTEN.pdf
FOTOCELDAS Y LOS DIFERENTES TIPOS QUE EXISTEN.pdfDanielAlejandroAguir2
 
Sanidad en alpacas, enfermedades infecciosas y parasitarias
Sanidad en alpacas, enfermedades infecciosas y parasitariasSanidad en alpacas, enfermedades infecciosas y parasitarias
Sanidad en alpacas, enfermedades infecciosas y parasitariasJilvertHuisaCenteno
 
Transporte y Manipulación de Explosivos - SUCAMEC
Transporte y Manipulación de Explosivos - SUCAMECTransporte y Manipulación de Explosivos - SUCAMEC
Transporte y Manipulación de Explosivos - SUCAMECamador030809
 
electricidad básica, ejemplos prácticos y ejercicios
electricidad básica, ejemplos prácticos y ejercicioselectricidad básica, ejemplos prácticos y ejercicios
electricidad básica, ejemplos prácticos y ejerciciosEfrain Yungan
 
Sistema Operativo Windows Capas Estructura
Sistema Operativo Windows Capas EstructuraSistema Operativo Windows Capas Estructura
Sistema Operativo Windows Capas EstructuraJairoMaxKevinMartine
 
Introduccion-a-los-tipos-de-cemento (1).pdf
Introduccion-a-los-tipos-de-cemento (1).pdfIntroduccion-a-los-tipos-de-cemento (1).pdf
Introduccion-a-los-tipos-de-cemento (1).pdfjhorbycoralsanchez
 
Sales Básicas Quimica, conocer como se forman las sales basicas
Sales Básicas Quimica, conocer como se forman las sales basicasSales Básicas Quimica, conocer como se forman las sales basicas
Sales Básicas Quimica, conocer como se forman las sales basicasPaulina Cargua
 
GeoS33333333333333333333333333333333.pdf
GeoS33333333333333333333333333333333.pdfGeoS33333333333333333333333333333333.pdf
GeoS33333333333333333333333333333333.pdffredyflores58
 
ACEROS DE PERFORACION, CARACTERISTICAS Y FICHAS TECNICAS.pptx
ACEROS DE PERFORACION, CARACTERISTICAS Y FICHAS TECNICAS.pptxACEROS DE PERFORACION, CARACTERISTICAS Y FICHAS TECNICAS.pptx
ACEROS DE PERFORACION, CARACTERISTICAS Y FICHAS TECNICAS.pptxaxelalejossantos
 
Dispositivos Semiconductores de Potencia BJT, MOSFET 01.pdf
Dispositivos Semiconductores de Potencia BJT, MOSFET 01.pdfDispositivos Semiconductores de Potencia BJT, MOSFET 01.pdf
Dispositivos Semiconductores de Potencia BJT, MOSFET 01.pdfdego18
 
PPT - MODIFICACIONES PRESUPUESTARIAS - Anexo II VF.pdf
PPT - MODIFICACIONES PRESUPUESTARIAS - Anexo II VF.pdfPPT - MODIFICACIONES PRESUPUESTARIAS - Anexo II VF.pdf
PPT - MODIFICACIONES PRESUPUESTARIAS - Anexo II VF.pdfDarwinJPaulino
 
EJERCICIOS DE PROPIEDADES INDICES DE MECÁNICA DE SUELOS
EJERCICIOS DE PROPIEDADES INDICES DE MECÁNICA DE SUELOSEJERCICIOS DE PROPIEDADES INDICES DE MECÁNICA DE SUELOS
EJERCICIOS DE PROPIEDADES INDICES DE MECÁNICA DE SUELOSLuisLopez273366
 
MATEMATICA BÁSICA FUNCIONES LOGARITMICAS
MATEMATICA BÁSICA FUNCIONES LOGARITMICASMATEMATICA BÁSICA FUNCIONES LOGARITMICAS
MATEMATICA BÁSICA FUNCIONES LOGARITMICASSALVADOR ALTEZ PALOMINO
 
Sistema de Base de Datos para renta de trajes
Sistema de Base de Datos para renta de trajesSistema de Base de Datos para renta de trajes
Sistema de Base de Datos para renta de trajesjohannyrmnatejeda
 
Química Analítica-U1y2-2024.pdf. Unidades 1 y 2
Química Analítica-U1y2-2024.pdf. Unidades 1 y 2Química Analítica-U1y2-2024.pdf. Unidades 1 y 2
Química Analítica-U1y2-2024.pdf. Unidades 1 y 2santiagoBernabei8
 

Último (20)

04-circuitos-comparadores de amplificadores operacionales.pptx
04-circuitos-comparadores de amplificadores operacionales.pptx04-circuitos-comparadores de amplificadores operacionales.pptx
04-circuitos-comparadores de amplificadores operacionales.pptx
 
SESIÓN 1 - Tema 1 - Conceptos Previos.pdf
SESIÓN 1 - Tema 1 - Conceptos Previos.pdfSESIÓN 1 - Tema 1 - Conceptos Previos.pdf
SESIÓN 1 - Tema 1 - Conceptos Previos.pdf
 
FOLIACIONES Y LINEACIONES GEOLOGÍA ESTRUCTURAL
FOLIACIONES Y LINEACIONES GEOLOGÍA ESTRUCTURALFOLIACIONES Y LINEACIONES GEOLOGÍA ESTRUCTURAL
FOLIACIONES Y LINEACIONES GEOLOGÍA ESTRUCTURAL
 
movimiento circular univormemente variado
movimiento circular univormemente variadomovimiento circular univormemente variado
movimiento circular univormemente variado
 
Capacitación Anexo 6 D.s. 023 seguridad y salud ocupacional
Capacitación Anexo 6 D.s. 023 seguridad y salud ocupacionalCapacitación Anexo 6 D.s. 023 seguridad y salud ocupacional
Capacitación Anexo 6 D.s. 023 seguridad y salud ocupacional
 
FOTOCELDAS Y LOS DIFERENTES TIPOS QUE EXISTEN.pdf
FOTOCELDAS Y LOS DIFERENTES TIPOS QUE EXISTEN.pdfFOTOCELDAS Y LOS DIFERENTES TIPOS QUE EXISTEN.pdf
FOTOCELDAS Y LOS DIFERENTES TIPOS QUE EXISTEN.pdf
 
Sanidad en alpacas, enfermedades infecciosas y parasitarias
Sanidad en alpacas, enfermedades infecciosas y parasitariasSanidad en alpacas, enfermedades infecciosas y parasitarias
Sanidad en alpacas, enfermedades infecciosas y parasitarias
 
Transporte y Manipulación de Explosivos - SUCAMEC
Transporte y Manipulación de Explosivos - SUCAMECTransporte y Manipulación de Explosivos - SUCAMEC
Transporte y Manipulación de Explosivos - SUCAMEC
 
electricidad básica, ejemplos prácticos y ejercicios
electricidad básica, ejemplos prácticos y ejercicioselectricidad básica, ejemplos prácticos y ejercicios
electricidad básica, ejemplos prácticos y ejercicios
 
Sistema Operativo Windows Capas Estructura
Sistema Operativo Windows Capas EstructuraSistema Operativo Windows Capas Estructura
Sistema Operativo Windows Capas Estructura
 
Introduccion-a-los-tipos-de-cemento (1).pdf
Introduccion-a-los-tipos-de-cemento (1).pdfIntroduccion-a-los-tipos-de-cemento (1).pdf
Introduccion-a-los-tipos-de-cemento (1).pdf
 
Sales Básicas Quimica, conocer como se forman las sales basicas
Sales Básicas Quimica, conocer como se forman las sales basicasSales Básicas Quimica, conocer como se forman las sales basicas
Sales Básicas Quimica, conocer como se forman las sales basicas
 
GeoS33333333333333333333333333333333.pdf
GeoS33333333333333333333333333333333.pdfGeoS33333333333333333333333333333333.pdf
GeoS33333333333333333333333333333333.pdf
 
ACEROS DE PERFORACION, CARACTERISTICAS Y FICHAS TECNICAS.pptx
ACEROS DE PERFORACION, CARACTERISTICAS Y FICHAS TECNICAS.pptxACEROS DE PERFORACION, CARACTERISTICAS Y FICHAS TECNICAS.pptx
ACEROS DE PERFORACION, CARACTERISTICAS Y FICHAS TECNICAS.pptx
 
Dispositivos Semiconductores de Potencia BJT, MOSFET 01.pdf
Dispositivos Semiconductores de Potencia BJT, MOSFET 01.pdfDispositivos Semiconductores de Potencia BJT, MOSFET 01.pdf
Dispositivos Semiconductores de Potencia BJT, MOSFET 01.pdf
 
PPT - MODIFICACIONES PRESUPUESTARIAS - Anexo II VF.pdf
PPT - MODIFICACIONES PRESUPUESTARIAS - Anexo II VF.pdfPPT - MODIFICACIONES PRESUPUESTARIAS - Anexo II VF.pdf
PPT - MODIFICACIONES PRESUPUESTARIAS - Anexo II VF.pdf
 
EJERCICIOS DE PROPIEDADES INDICES DE MECÁNICA DE SUELOS
EJERCICIOS DE PROPIEDADES INDICES DE MECÁNICA DE SUELOSEJERCICIOS DE PROPIEDADES INDICES DE MECÁNICA DE SUELOS
EJERCICIOS DE PROPIEDADES INDICES DE MECÁNICA DE SUELOS
 
MATEMATICA BÁSICA FUNCIONES LOGARITMICAS
MATEMATICA BÁSICA FUNCIONES LOGARITMICASMATEMATICA BÁSICA FUNCIONES LOGARITMICAS
MATEMATICA BÁSICA FUNCIONES LOGARITMICAS
 
Sistema de Base de Datos para renta de trajes
Sistema de Base de Datos para renta de trajesSistema de Base de Datos para renta de trajes
Sistema de Base de Datos para renta de trajes
 
Química Analítica-U1y2-2024.pdf. Unidades 1 y 2
Química Analítica-U1y2-2024.pdf. Unidades 1 y 2Química Analítica-U1y2-2024.pdf. Unidades 1 y 2
Química Analítica-U1y2-2024.pdf. Unidades 1 y 2
 

Introduccion a C++.pdf

  • 1. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 1 Introducción a ANSI C y Visual C++ El propósito de este boletín de prácticas es servir como material de apoyo y consulta para los aspectos esenciales de C que se utilizarán en MTP. También se ha incluido una breve introducción al uso de Visual C++ y en particular a su depurador (debugger). Introducción a ANSI C 1 Aspectos básicos de C Todo programa en C tiene una función principal por la que comienza la ejecución (main). 1.1 Declaración de variables Tipos Básicos • char, un carácter, visto también como valores enteros desde -128 a 127. • int, entero, valor desde -32768 a 32767. • long, entero largo, valor desde -215 a 215 -1. • float, coma flotante simple precisión, con decimales. • double, coma flotante doble precisión. Para definir variables locales a una función, después de la llave que abre una función especificar el tipo seguido de una lista de variables separada por comas, y finalizada con “;” . /* Este es mi primer programa en C */ #include<stdio.h> main() { printf(“Hola mundon”); } Comentarios Inclusión de la definición de funciones de librería Función principal Código del programa main() { int i,j,k; char tecla; ...
  • 2. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 2 Tipos Estructurados • Arrays n-dimensionales: char nombre[50]; float matriz[20][20]; para acceder a los elementos de los array: c=nombre[0]; matriz[5][2]=2.5; • Registros struct persona{ int edad; int peso; char nombre[40]; } director, recepcionista, vendedores[20]; Para acceder a los campos de un registro hay que usar el operador punto ‘.’: director.edad=40; recepcionista.peso=80; vendedores[5].nombre[2]=‘p’; Se pueden definir tipos para usarlos en muchos lugares, con la palabra reservada typedef: typedef struct { double real, imaginary; } complex; Las estructuras pueden ser asignadas, pasadas a funciones y devueltas por las mismas, pero no pueden ser comparadas, por lo que: complex a, b; a.real=0; a.imaginary=0; b=a; es correcto, pero lo que sigue no lo es y debe hacerse campo a campo. if(a==b) Esto es un string Ojo, siempre empiezan por 0 Nombre identificador del struct Campos Variables de tipo registro persona
  • 3. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 3 Constructores Estructurados 1. Selección if(i==3) /* para la desigualdad usar != */ j=4; else{ /* las llaves son necesarias si hay más de una sentencia */ j=5; k=6; } switch(i){ /* la expresión se evalúa a entero o carácter */ case 1: printf(“i vale uno”); break; case 2: printf(“i vale dos”); break; default: printf(“i no vale ni uno ni dos”); } 2. Bucles while(i<30){ /* test al principio del bucle */ hacer_cosas(i); i=i+1; /* también se puede usar i++ */ } do{ hacer_cosas(i); /* el código se ejecuta al menos una vez */ i=i+1; }while(i<30); /* test al final del bucle */ for(n=0; n<200; n++){ /*for(inicialización;test;actualización)*/ hacer_cosas(i); } for(i=3;i<5;i=i+1){ hacer_cosas(i); } i=3; while (i<5){ hacer_cosas(i); i=i+1; end; equivalencia entre el for y el while
  • 4. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 4 Se puede modificar el comportamiento de los bucles ejecutando las sentencias: continue, que interrumpe el ciclo actual y va al siguiente ciclo, y break, que interrumpe el bucle. Por ejemplo: el siguiente bucle sólo ejecuta la sentencia printf cuando la variable i toma los valores 0 y 2. 1.2 Punteros Dado un tipo T, T* es el tipo “puntero a T”. Es decir, una variable de tipo T* puede contener la dirección de un objeto de tipo T. char *strp; /* strp es un puntero a char */ char car=`a`; /* car es un char */ strp=&car; strp: &car car: a car=*strp; strp=car; /* error*/ 1.3 Entrada/Salida La definición estándar de C no incluye sentencias para la E/S de información. C tiene definidas las funciones de E/S en bibliotecas de funciones aparte. Para poder usarlas se deben incluir las definiciones de las funciones (stdio.h) en nuestros programas mediante la directiva #include< > Entrada scanf es una función de entrada de datos, según el formato definido en el string del primer argumento, que guarda la información introducida en las variables colocadas en el resto de los argumentos. Algunos formatos reconocidos: %c char %s string %d int %ld long %f float ... i=0; while(i<5){ if(i==1){ i=i+1; continue; } if(i==3) break; printf(“i = %dn”, i); i++; }
  • 5. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 5 Para indicar las variables en las que se desea que se guarde la información se deben pasar punteros a ellas. Para ello basta con anteponer el símbolo & al nombre de la variables, excepto en el caso de los strings. Ejemplos: scanf(“%d”, &i); scanf(“%d”, &director.edad); scanf(“%s”, vendedor[i].nombre); scanf(“%f%f”, &a.real, &a.imaginary); scanf(“%f”, &matriz[i][j]); no hace falta el & por ser un string
  • 6. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 6 Salida printf es una función de salida de información. Su primer argumento es un string con el formato que debe tener la información que se muestre. Los siguientes argumentos son las variables que contienen la información que se quiere mostrar. Los formatos reconocidos son los mismos que acepta la función scanf. Se pueden emplear algunos caracteres especiales como: n Imprime un salto de línea. t Imprime un tabulador. Imprime la barra invertida. Ejemplos: printf(“La edad del director es %dn”, director.edad); printf(“Vendedor: %dntNombre: %sntEdad: %dntPeso: %dn”, i, vendedor[i].nombre, vendedor[i].edad, vendedor[i].peso); 1.4 Ejercicios propuestos a. Escribir un programa que calcule el máximo, mínimo y la media de una lista indefinida de números enteros positivos. En el caso de introducir un número negativo, dicho número debe ser rechazado indicando el motivo. Un cero indicará que la lista de números se ha acabado. b. Escribir un programa que lea un vector de cinco cifras y compruebe si es capicúa. c. Escribir un programa que muestre por pantalla las tablas de multiplicar y dividir que el usuario quiera, y finalice cuando el usuario indique que desea ver la tabla del cero. d. Escribir un programa que lea una matriz cuadrada de enteros y escriba la diagonal inversa.
  • 7. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 7 2 Funciones en C C no tiene procedimientos, sólo funciones. Sus definiciones no pueden ser anidadas pero todas excepto main pueden ser llamadas recursivamente. 2.1 Declaración de funciones <tipo_retorno><nombre_función>(<lista_declaración _parámetros formales>); Ejemplos de funciones en C: • void dibujar(void); //sin argumentos y //sin valor de retorno • int dibujar(void); //sin argumentos y //devuelve un int • int calcula_producto(int x, int y); // con argumentos de // tipo int y devuelve int En un fichero de código C las funciones deben declararse o definirse antes de ser utilizadas. En el primer caso basta con hacer la declaración al principio del fichero, así ya no importará el orden de definición de las funciones. En el segundo caso, se evita hacer las declaraciones pero se debe poner atención al orden de definición de las funciones para que siempre la definición sea anterior a su utilización, lo cual resulta incómodo cuando se trabaja con muchas funciones en un fichero. Como veremos más adelante, cuando las funciones están definidas en un fichero distinto al cual donde se utilizan, necesariamente debe hacerse una declaración de dichas funciones. 2.2 Implementación de funciones en C Cada función llamada en un programa debe estar implementada en algún sitio (y sólo una vez). La sintaxis es: <tipo_retorno><nombre_función>(<lista_declaración _parámetros formales>) { <variables locales> <cuerpo> } Ejemplo de implementación de funciones en C: int calcula_producto(int x,int y){ int rdo; rdo=x*y; return rdo; } Una función equivalente sería: int calcula_producto(int x,int y) {return x*y;}
  • 8. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 8 2.3 Invocación de funciones en C La invocación a una función se hace poniendo el identificador seguido de paréntesis (obligatorios aunque no tenga parámetros) dentro de los cuales pondremos los parámetros. Los parámetros deben ser del mismo tipo que el prototipo y la definición. Ejemplo: ... int a,b,rdo; a=5; b=7; rdo=calcula_producto(a,b); ... 2.4 Retorno de valores en C La sentencia de retorno es necesaria para poder devolver valores desde funciones. Su sintaxis es: return expresion; 2.5 Parámetros por valor y por referencia Por defecto, los parámetros en C se pasan por valor. Ejemplo: Una función para intercambiar el valor de dos variables: void intercambio(int a,int b){ int temp=a; a=b; b=temp; } void main(){ int a=10,b=20; intercambio(a,b); } Para pasar parámetros por referencia se utilizan punteros y lo que se pasa a la función es un puntero a los parámetros cuyo contenido se desea modificar. void intercambio(int *a,int *b){ (1) int temp=*a; (2) *a=*b; *b=temp; } void main(){ int a=10,b=20; intercambio(&a,&b); (3) } (1) int *a indica que la variable a es un puntero a entero (contiene la dirección de una variable entera). (2) el operador “*” referencia al puntero. *p es la variable entera apuntada por p. ¿Se intercambian los valores de a y b?
  • 9. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 9 (3) en la llamada se pasan referencias a variables enteras utilizando el operador “&”. ¿Se cambian los valores de a y b?. Véamos cuál sería la ejecución de la llamada. a) int a=10,b=20; b) intercambio(&a,&b); // como primer parámetro se pasa la // dirección de a y como segundo parámetro // la dirección de b c) int temp=*a; // temp=10; d) *a=*b; e) *b=temp; 2.6 Ejercicio Propuesto Haga un programa que contenga tres funciones: una función lee el número, otra calcula el cuadrado y otra visualiza el resultado. En pantalla debería aparecer algo así: Dame un número: 5 5*5=25
  • 10. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 10 3 Trabajando con funciones y variables en distintos ficheros El diseño de un sistema, en nuestro caso representado básicamente por el diagrama de estructura, debe implementarse físicamente en 1 o más ficheros de código fuente. Para la mayoría de los sistemas, es inviable programarlos, probarlos y mantenerlos considerando como único componente un fichero con todo código fuente. Tampoco resulta práctico utilizar para cada módulo un fichero de código fuente. Con lo cual la decisión normalmente considera el codificar varios módulos en un mismo fichero. El criterio de agrupación debe incluir aspectos tales como: dependencia entre módulos (por invocaciones entre ellos o porque comparten información), despliegue de los módulos en los mismos nodos (cuando el sistema es distribuido), etc. En C tenemos dos formas básicas de trabajar con varios ficheros en una aplicación: incluyendo un fichero en otro mediante directivas del compilador (#include) o mediante la declaración de funciones o variables extern. 3.1 Inclusión de ficheros en C Cuando el preprocesador encuentra una directiva #include entonces busca el archivo especificado en la instrucción y lo incluye en el fichero actual. La directiva #include en el archivo de código fuente se sustituye por el texto del archivo incluido. La operación equivale a que el usuario teclee toda la información que éste contiene. El nombre del archivo puede venir de dos formas: #include <stdio.h> // busca en directorios estándar del sistema #include "mifichero.h" // busca en el directorio en el que se esté // trabajando ¿Por qué incluir en un fichero otro fichero? Los ficheros de encabezamiento (o cabeceras), contienen entre otras cosas: • Constantes explícitas. • Declaraciones de funciones. • Declaraciones de tipos. Ejemplo Supongamos que se desea utilizar valores booleanos, es decir, queremos emplear CIERTO y FALSO en lugar de 1 y 0, respectivamente. Podríamos crear un fichero que se llamase, por ejemplo, "bool.h", que contuviera estas definiciones: #define BOOL int #define CIERTO 1 #define FALSO 0 Para poder utilizar CIERTO y FALSO incluiremos el fichero bool.h en donde se quisieran utilizar. #include "bool.h" int main(void){ BOOL v1; v1=CIERTO; v1=FALSO;}
  • 11. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 11 3.2 Declaraciones Extern Las funciones y las variables definidas en ficheros pueden ser accedidas desde otros ficheros donde deberían ser declaradas usando la palabra reservada "extern". En el caso de las variables es obligatorio explicitar si son o no extern. En el caso de las funciones no es necesaria su colocación, ya que por defecto las funciones son extern, sin embargo debe siempre declararse el prototipo de estas funciones en el fichero donde serán utilizadas y antes de hacer referencia a ellas. 3.3 Ejercicio Resuelva los ejercicios a, b y c propuestos en la sección 1, pero implementando cada función en un fichero distinto (main es también una función).
  • 12. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 12 4 Manejo de archivos en C Este capítulo es una breve introducción al manejo de archivos en C. Se describen solamente las operaciones básicas: apertura, lectura, escritura y cierre de archivos. Lo suficiente para poder manejar archivos binarios mediante acceso secuencial. Las funciones de manejo de archivos están definidas en la librería stdio.h, por lo que para poder utilizar archivos en un programa C debe incluirse dicha librería: # include <stdio.h> 4.1 Declaración de archivos En C se define un manejador del archivo, en forma de puntero al tipo FILE: FILE *fich; /* fich es un manejador de Archivo */ Ligado a cada manejador existe un indicador de posición actual asociado al archivo. Este indicador se actualiza en cada operación de lectura o escritura. Por ejemplo, después de leer un bloque de datos el indicador apuntará a la siguiente posición en el archivo, a partir de donde se seguirán leyendo datos. 4.2 Apertura de archivos Para abrir un archivo existente o para crear un nuevo archivo se utiliza la función fopen cuya cabecera es: FILE *fopen(const char *Nombre_archivo, const char *modo); fopen devuelve un puntero que es el manejador del archivo. Si alguna operación no es posible devuelve NULL (por ejemplo, si se intenta abrir un archivo que no existe). Sus parámetros son: Nombre_archivo: es una cadena con el nombre del archivo. Modo: es una cadena que indica, el modo de apertura: r abre un archivo existente sólo en modo lectura. El puntero se posiciona al comienzo del archivo. w crea el archivo para escritura, si el archivo ya existe lo sobreescribe. El puntero se posiciona al comienzo del archivo. a abre el archivo para escribir al final del mismo (append). Si no existe lo crea. El puntero se posiciona al final del archivo. r+ abre un archivo existente para actualización (lectura y escritura). El puntero se posiciona al comienzo del archivo. w+ crea un nuevo archivo para actualización, si ya existe lo sobreescribe. El puntero se posiciona al comienzo del archivo. a+ crea un nuevo archivo para actualización al final del archivo. Si no existe lo crea. El puntero se posiciona al final del archivo. El tipo de archivo: b binario. t texto. Ejemplo: fich = fopen(“FicheroB”, “rb”);
  • 13. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 13 Abre el archivo binario “FicheroB” en modo lectura, si “FicheroB” no existe devuelve NULL. fich = fopen(“FicheroT”, “w+t”); Crea el archivo de texto con nombre “FicheroT” para lectura y escritura. Si no puede crear el archivo devuelve NULL. 4.3 Cierre de archivos Para cerrar un archivo se utiliza la función fclose. Si se quiere cambiar el modo de apertura de un archivo (p.e. pasar de escritura a lectura o viceversa) previamente debe cerrarse. int fclose (FILE *fich); fclose cierra todos los buffers asociados con el manejador de archivo fich y devuelve 0 si se ha cerrado con éxito y EOF (end-of-file, final de fichero) si no. Ejemplo: fclose(fich); /* cierra el archivo apuntado por ‘fich’ */ 4.4 Operación de Escritura: Para realizar la escritura de un bloque de datos en un archivo se utiliza la función fwrite. Sólo podrá llevarse a cabo la escritura si el archivo está abierto para escritura o para actualización. size_t fwrite(void *ptr, size_t talla, size_t n,FILE *fich) fwrite escribe n elementos de una talla fija desde la estructura apuntada por ptr en el archivo fich. Devuelve el número de elementos almacenados. En caso de realizarse la operación con éxito ese número coincide con n; en caso contrario, el valor será menor que n. Ejemplo: typedef struct { int a; char b; } Registro; main() { FILE *fich; Registro Reg; if ((fich = fopen(“FicheroB”, “wb”))==NULL) { printf(“Error: no pudo crearse el archivon”); return 1; } Reg.a= 10; Reg.b= ‘c’; fwrite(&Reg,sizeof(Reg),1,fich); fclose(fich); } Primero, crea el archivo para escritura. Si no puede, muestra un mensaje de error y finaliza. La instrucción fwrite almacena en fich 1 elemento de tamaño sizeof(Reg) que está en la
  • 14. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 14 variable Reg. La función sizeof devuelve el tamaño en bytes del elemento pasado como argumento. 4.5 Operación de Lectura Para realizar la lectura de un bloque de datos desde un archivo se utiliza la función fread. Sólo puede llevarse a cabo la operación si el archivo está abierto para lectura o para actualización. size_t fread(void *ptr, size_t talla, size_t n, FILE *fich) fread lee un número n de elementos de una talla fija (expresada en bytes) desde un archivo fich y los almacena en la dirección apuntada por ptr. Devuelve el número de elementos leídos. En caso de alcanzar el final del archivo, devuelve el número de elementos leídos que será menor que n (pudiendo ser 0). El tamaño de la memoria reservada apuntada por ptr debe ser al menos de talla × n bytes. El indicador de posición del archivo apunta al siguiente bloque de datos a leer. Así, lecturas sucesivas recorrerán el archivo secuencialmente. Ejemplo: main() { FILE *fich; Registro Reg; if ((fich = fopen(“FicheroB”, “rb”))==NULL) { printf(“Error: no pudo abrirse el archivon”); return 1; } fread(&Reg, sizeof(Reg), 1, fich); fclose(fich); } Primero, abre el archivo para lectura. Si no puede, muestra un mensaje de error y finaliza. La instrucción fread lee, desde el archivo fich, 1 elemento de datos de tamaño sizeof(Reg) y lo guarda en la variable Reg. Tenga cuidado con el uso de punteros. Observe que el primer argumento de fread es un puntero, por lo que en el ejemplo se pasa la dirección de Reg (es decir, &Reg). Si Reg se hubiera declarado como un puntero a Registro entonces la instrucción sería: Registro *Reg; ... fread(Reg, sizeof(*Reg), 1, fich); Con estas operaciones es suficiente para recorrer un archivo de forma secuencial y almacenar información al final del archivo. Cualquier otra operación sobre archivos como borrado de datos, ordenación, inserción en una posición intermedia, etc. requiere el uso de archivos auxiliares en los cuales se almacena temporalmente la información. Existen otras funciones como fseek (para situar el puntero al archivo en una posición determinada), rewind (que sitúa el puntero al comienzo del archivo), ftell (que indica la posición del puntero) etc. 4.6 Búsqueda Secuencial En algunos módulos de la aplicación se debe implementar un recorrido secuencial de un archivo hasta encontrar un registro determinado. Es el caso de los módulos de verificación tales como
  • 15. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 15 "Verificar Tarjeta Permitida”. Puede basarse en la siguiente plantilla para implementar dichos módulos: FUNCIÓN VALIDAR (campo_búsqueda) RETORNA válido Entrada: campo_búsqueda, campo del registro por el cual buscar Salida: válido= 1 (válido), 0 (no válido), -1 (no encontrado) INICIO ABRIR_ARCHIVO; encontrado = FALSO; final_de_archivo = LEER_DE_ARCHIVO (registro); MIENTRAS (NO final_de_archivo) Y (NO Encontrado) HACER SI (campo_búsqueda = registro.campo_búsqueda) ENTONCES encontrado = CIERTO; FIN_SI final_de_archivo = LEER_DE_ARCHIVO (registro); FIN_MIENTRAS; CERRAR_ARCHIVO; SI (NO Encontrado) RETORNAR -1; SI (ES registro VÁLIDO) RETORNAR 1; SI NO RETORNAR 0; FIN A continuación se muestra como ejemplo la implementación de una función que valida si determinado campo de un registro cumple una condición. En concreto, si el campo “saldo” de un registro del fichero “FcuentasB”, cuya clave de acceso es “n_cuenta”, es mayor que 1000. int validar_saldo_mayor_1000 (Numero_Cuenta n_cuenta) /* Entrada: n_cuenta número de cuenta a buscar Salida: 1 si saldo > 1000; 0 si saldo <= 1000; -1 si no puede abrir archivo */ { FILE *FCuentas; int encontrado = 0; Reg_Cuenta rc; if ((FCuentas=fopen("FcuentasB","rb"))==NULL) return -1; else { while (!encontrado && fread(&rc,sizeof(rc),1,FCuentas) ) /* el registro buscado es aquel tal que rc.n_cuenta=n_cuenta la comparación debe hacerse campo a campo */ if (!strcmp(rc.n_cuenta.cod_banco,n_cuenta.cod_banco) && !strcmp(rc.n_cuenta.cod_sucursal,n_cuenta.cod_sucursal) && !strcmp(rc.n_cuenta.cod_cuenta,n_cuenta.cod_cuenta)) encontrado=1; fclose(FCuentas); if (!encontrado) return -1; /* a continuación se valida el registro */ if (rc.saldo > 1000) return 1; else return 0; } }
  • 16. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 16 4.7 Actualización de un registro Los módulos que actualizan un almacen de datos deben buscar el registro a actualizar, modificarlo y guardarlo en el almacen de datos. Es el caso de módulos como Actualizar Saldo. Una posible plantilla para esos módulos sería: FUNCIÓN ACTUALIZAR(campo_búsqueda, valor_actualización) RETORNA ok Entrada: campo_búsqueda, campo del registro por el cual buscar valor_actualización, valor a asignar al campo que se va a actualizar Salida: ok: 1 (éxito) 0 (no encontrado o problemas de archivo) INICIO ABRIR_ARCHIVO_COPIA; (para escritura) ABRIR_ARCHIVO_ORIGEN; (para lectura) final_de_archivo = LEER_DE_ARCHIVO_ORIGEN (registro); MIENTRAS (NO final_de_archivo) HACER SI (campo_búsqueda = registro.campo_búsqueda) ENTONCES Registro.campo_a_actualizar=valor_actualización; FIN_SI ESCRIBIR_EN_ARCHIVO_COPIA (registro); final_de_archivo = LEER_DE_ARCHIVO_ORIGEN (registro); FIN_MIENTRAS; CERRAR_ARCHIVO_ORIGEN; CERRAR_ARCHIVO_COPIA; ARCHIVO_ORIGEN = ARCHIVO_COPIA; FIN A continuación se muestra como ejemplo la implementación de una función que actualiza un campo de un registro. En concreto, el campo “cantidad permitida” de un registro del archivo “FtarjetasB” cuya clave de acceso es “n_tarjeta”. int modificar_cantidad_permitida (Numero_Tarjeta n_tarjeta, float cantidad) /* Entrada: n_tarjeta, número de tarjeta a buscar cantidad, valor de actualización del campo 'cantidad_permitida' Salida: 1 si se ha actualizado con éxito, 0 si no (problemas con archivos, o no encuentra n_tarjeta) */ { FILE *Fcopia, *Ftarjetas; Reg_Tarjeta r; int encontrado=0; if ((Fcopia=fopen("Fcopia","wb"))==NULL) return 0; if ((Ftarjetas=fopen("FtarjetasB","rb"))==NULL) return 0; while (fread(&r,sizeof(r),1,Ftarjetas)) { if (!strcmp(r.num_tarjeta.cod_banco,n_tarjeta.cod_banco) && !strcmp(r.num_tarjeta.cod_tarjeta,n_tarjeta.cod_tarjeta)){ encontrado=1; r.cantidad_maxima=cantidad; /* se modifica el registro */ } fwrite(&r,sizeof(r),1,Fcopia); } fclose(Ftarjetas); fclose(Fcopia); remove("FtarjetasB");
  • 17. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 17 rename("Fcopia","FtarjetasB"); if (encontrado) return 1; else return 0; }
  • 18. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 18 5 Manejo de cadenas en C Para el manejo de cadenas (‘strings’) en C, este provee una librería <string.h>. En ésta se definen varias funciones para manipular cadenas. 5.1 Definición de cadenas Una cadena en C puede definirse como un vector de caracteres. Por ejemplo, en char nombre[10]; se define la cadena nombre con un máximo de 10 caracteres, incluyendo el símbolo de fin de cadena ‘0’. Las operaciones básicas con cadenas son: 5.2 Copia de cadenas char *strcpy(char *destino, const char *origen); strcpy copia la cadena origen en la cadena destino hasta que encuentra la marca de terminación ‘0’. Como valor de retorno devuelve la cadena origen. Ejemplo: main() { char nombre1[10], nombre2[10]; strcpy(nombre1, “Juan”); strcpy(nombre2, nombre1); } Tanto nombre1 como nombre2 contienen la cadena “Juan”. char *strncpy(char *destino, const char *origen, size_t max); strncpy copia la cadena origen en la cadena destino hasta un máximo de max caracteres o hasta que encuentra la marca de terminación ‘0’. Como valor de retorno devuelve la cadena origen. 5.3 Comparación de cadenas: int strcmp(const char c1, const char c2) strcmp compara las cadenas c1 y c2. Devuelve 0 si son iguales, un valor menor que 0 si c1 < c2 y un valor mayor que 0 si c1 > c2. Ejemplo: main() { char nombre1[10], nombre2[10]; strcpy(nombre1, “Juan”); strcpy(nombre2, “Luis”); if (strcmp(nombre1,nombre2)==0) printf(“Iguales”); else printf(“Distintos”); } int strncmp(const char c1, const char c2, size_t max)
  • 19. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 19 strncmp compara las cadenas c1 y c2 hasta un máximo max de caracteres. Devuelve 0 si son iguales, un valor menor que 0 si c1 < c2 y un valor mayor que 0 si c1 > c2. 5.4 Longitud de cadenas size_t strlen(const char c) strlen devuelve la longitud de la cadena c, sin contar el carácter de terminación de cadenas. Ejemplo: main() { char nombre1[10]; strcpy(nombre1, “Juan”); printf(“Longitud de nombre1 es %d”, strlen(nombre1)); } 5.5 Concatenar cadenas: char strcat(const char destino, const char origen) strcat concatena una copia de la cadena origen al final de la cadena destino. Añade el carácter de terminación al final de la cadena destino. Devuelve la cadena concatenada. Ejemplo: main() { char nombre1[10]; strcpy(nombre1, “Juan”); strcat(nombre1,” Luis”); /* nombre1 contiene “Juan Luis” */ } char strncat(const char destino,const char origen,size_t max) strncat concatena una copia de la cadena origen al final de la cadena destino hasta un máximo de max caracteres. Añade el carácter de terminación al final de la cadena destino.
  • 20. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 20 6 Variables Estáticas Constituyen una clase de almacenamiento diferente a las variables automáticas y extern. Una variable estática se especifica anteponiendo a la declaración normal la palabra static. Por ejemplo, una variable de tipo int y estática se define como: static int id; Se definen locales a una función o a un fichero. 6.1 Variables estáticas locales a una función En este caso, la variable estática se diferencia de la variable automática en que su existencia es permanente, en lugar de aparecer y desaparecer cada vez que se activa la función. En el siguiente ejemplo se utiliza una variable estática como buffer de una línea y un índice que nos indica cuál fue el carácter accedido en la última invocación de la función. int func(int x){ static int y; /* variable estática */ y++; /* el valor de la y se incrementa cada */ return (x+y); /* vez que se llama a la funcion */ } 6.2 Variables estáticas locales a un fichero En este caso, la variable será accesible desde todas las funciones que se declaren dentro del mismo fichero, y será invisible fuera del archivo en que está declarada. static tiene sentido de permanencia y de privacidad. Veamos un ejemplo: /* fichero1.c */ static int valor = 0; int leer(void) { return(valor); } void escribir(int nuevo_valor) { valor = nuevo_valor; } /* fichero2.c */ #include <stdio.h> main() { int x, y; x = leer(); x++; escribir(x); y = leer(); printf(“valor: %d”,y); }
  • 21. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 21 La representación del “cluster de información” del ejemplo es la siguiente: Escribir Leer valor nuevo_valor valor a2 a1 6.3 Ejercicio Utilizando el ejemplo anterior, modificar las funciones para que se escriba y se lea una estructura con un campo de tipo int y otro de tipo char.
  • 22. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 22 Introducción a Visual C++ En esta sección se indican los pasos básicos para crear en Visual C++ un proyecto del tipo aplicación de consola. También, estudiando un ejemplo, se incluye una breve presentación del uso del depurador de Visual C++. Para crear un nuevo proyecto se activa el menú File | New. En Projects se selecciona Win32 Console Application y se da un nombre al proyecto (que será el nombre de la carpeta donde se guardarán los fuentes, compilados y ejecutable) (ver Figura 1). Después se escoge como tipo de proyecto Empty Project. Figura 1: Creación de un nuevo proyecto Para crear un nuevo archivo fuente se activa File | New, y posteriormente C++ source file en Files. En el caso de que el fichero ya esté creado, y queramos añadirlo al proyecto, se activa la opción Project | Add to project | Files (ver Figura 2). En nuestro caso el fichero ya está creado, trabajaremos con el fichero calcularSumaOPromedioConMain.c. El código del fichero se muestra a continuación:
  • 23. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 23 #include <stdio.h> int calcularSuma(int vectorEnteros[], int tamanyo) { int i, suma = 0; for (i = 0; i < tamanyo; i++) { suma = suma + vectorEnteros[i]; } return (suma); } int calcularPromedio(int vectorEnteros[], int tamanyo) { int suma; int media; suma = calcularSuma(vectorEnteros, tamanyo); media = suma / tamanyo; return (media); } float calcularSumaOPromedio(int opcion, int vectorEnteros[], int tamanyo) { float resultado = 0.0; switch (opcion) { case 1: resultado = (float) calcularSuma(vectorEnteros, tamanyo); break; case 2: resultado = (float) calcularPromedio(vectorEnteros, tamanyo); break; } return (resultado); } void main() { int vector[] = { 2, 2, 2, 4, 4, 4}; printf("%f",calcularSumaOPromedio(1,vector,6)); printf("%f",calcularSumaOPromedio(2,vector,6)); } Una vez introducido el fichero, éste se ha compilar. Para ello se activa Build | Compile (Ctrl + F7). Posteriormente se ha de enlazar, por lo que se elige Build | Build (F7). Ahora ya se puede ejecutar el archivo a través de la opción Build | Execute (Ctrl + F5). Los tres pasos se pueden hacer de una sola vez con esta última opción. Tras ejecutar el proyecto se observa que éste se ejecuta sin problemas. Sin embargo, si se sustituye en la función main las líneas printf("%f",calcularSumaOPromedio(1,vector,6)); printf("%f",calcularSumaOPromedio(2,vector,6)); por estas otras: printf("%f",calcularSumaOPromedio(1,vector,0)); printf("%f",calcularSumaOPromedio(2,vector,0)); y se repiten los tres últimos pasos (compilar, enlazar y ejecutar), la ejecución falla, mostrando un mensaje de error (ver Figura 3).
  • 24. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 24 Figura 2: Añadiendo un fichero al proyecto Figura 3: Mensaje de error de ejecución
  • 25. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 25 Para descubrir dónde se produce el error utilizaremos el debugger que incorpora Visual C++. Lo primero que hay que establecer son los puntos de ruptura (breakpoints), que permiten detener la ejecución del programa en una determinada línea. Para insertar un punto de ruptura (que se identifica como un punto rojo), se selecciona la línea donde se quiere insertar, y posteriormente con el botón derecho se invoca Insert/Remove Breakpoint. Para poder ejecutar ahora el código, se selecciona la opción Build | Start Debug | Go (F5). Aparece entonces una flecha amarilla que indica qué línea del código va a ser la siguiente en ejecutarse. Para avanzar en la ejecución del programa se pulsan las teclas F11 (Step into), que permite ver la ejecución paso a paso dentro de una función, o F10 (Step over), que ejecuta de una vez el código de la función. Insertar un punto de ruptura en la línea printf("%f",calcularSumaOPromedio(1,vector,0)) de la función main e iniciar el debugger (ver Figura 4). Figura 4: Ejecución con el depurador En la parte inferior de la pantalla pueden verse las variables del programa junto con los diferentes valores que van tomando durante la ejecución. En cualquier momento se puede abandonar el debugger con la opción Debug | Stop Debugging (Shift + F5). Si se ejecuta paso a paso el fichero (con F10, F11) hasta llegar a la situación descrita en la Figura 5, y se observa el valor de las variables, se comprueba que tanto suma como tamanyo tienen el valor 0.
  • 26. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 26 Figura 5: Paso previo a la instrucción de división por 0 Llegados a este punto, y tras pulsar de nuevo F11, se muestra un mensaje de error, y la ejecución finaliza debido a la excepción producida al intentar realizar una división por 0 (ver Figura 6). La solución a este problema consistiría en controlar el valor de la variable tamanyo en las funciones que hacen uso de ella.
  • 27. Metodología y Tecnología de la Programación Departamento de Sistemas Informáticos y Computación. Universidad Politécnica de Valencia. 27 Figura 6: Mensaje de error de ejecución estando en modo de depuración