U.A.B.C. Facultad de Ingeniería Programación Estructurada UNIDAD VI UNIDAD VI Archivos. 6.1 INTRODUCCION Los datos que hemos tratado hasta el momento han residido en la memoria principal. Sin embargo, las grandes cantidades de datos se almacenan normalmente en un dispositivo de memoria secundaria. Estas colecciones de datos se conocen como archivos (antiguamente archivos). Un archivo es un conjunto de datos estructurados en una colección de entidades elementales o básicas denominadas registros que son de igual tipo y constan a su vez de diferentes entidades de nivel más bajos denominadas campos. En cuanto al tipo de acceso, en C podemos clasificar los archivos según varias categorías: 1. Dependiendo de la dirección del flujo de datos: De entrada: los datos se leen por el programa desde el archivo. De salida: los datos se escriben por el programa hacia el archivo. De entrada/salida: los datos pueden se escritos o leídos. 2. Dependiendo del tipo de valores permitidos a cada byte: De texto: sólo están permitidos ciertos rangos de valores para cada byte. Algunos bytes tienen un significado especial, por ejemplo, el valor hexadecimal 0x1A marca el fin de archivos. Si abrimos un archivo en modo texto, no será posible leer más allá de un byte con ese valor, aunque el archivo sea más largo. Binarios: están permitidos todos lo valores para cada byte. En estos archivos el final del archivo se detecta de otro modo, dependiendo del soporte y del sistema operativo. La mayoría de las veces se hace guardando la longitud del archivo. Cuando queramos almacenar valores enteros, o en coma flotante, o imágenes, etc, deberemos usar este tipo de archivos. 3. Según el tipo de acceso: Archivos secuenciales: imitan el modo de acceso de los antiguos archivos secuenciales almacenados en cintas magnéticas y Archivos de acceso aleatorio: permiten acceder a cualquier punto de ellos para realizar lecturas y/o escrituras. 4. Según la longitud de registro: Longitud variable: en realidad, en este tipo de archivos no tiene sentido hablar de longitud de registro, podemos considerar cada byte como un registro. También puede suceder que nuestra aplicación conozca el tipo y longitud de cada dato almacenado en el archivo, y lea o escriba los bytes necesarios en cada ocasión. Otro caso es cuando se usa una marca para el final de registro, por ejemplo, en archivos de texto se usa el carácter de retorno de línea para eso. En estos casos cada registro es de longitud diferente. Longitud constante: en estos archivos los datos se almacenan en forma de registro de tamaño contante. En C usaremos estructuras para definir los Ing. Pablo M. Navarro Álvarez Página # 1 U.A.B.C. Facultad de Ingeniería Programación Estructurada UNIDAD VI registros. C dispone de funciones de librería adecuadas para manejar este tipo de archivos. Mixtos: en ocasiones pueden crearse archivos que combinen los dos tipos de registros, por ejemplo, dBASE usa registros de longitud constante, pero añade un registro especial de cabecera al principio para definir, entre otras cosas, el tamaño y el tipo de los registros. Es posible crear archivos combinando cada una de estas categorías, por ejemplo: archivos secuenciales de texto de longitud de registro variable, que son los típicos archivos de texto. Archivos de acceso aleatorio binarios de longitud de registro constante, normalmente usados en bases de datos. Y también cualquier combinación menos corriente, como archivos secuenciales binarios de longitud de registro constante, etc. En c, un archivo es un concepto lógico que puede aplicarse a muchas cosas desde archivos de disco hasta terminales o una impresora. Se asocia una secuencia con un archivo específico realizando una operación de apertura. Una vez que el archivo está abierto, la información puede ser intercambiada entre este y el programa. Se puede conseguir la entrada y la salida de datos a un archivo a través del uso de la biblioteca de funciones; C no tiene palabras claves que realicen las operaciones de E/S. A continuación se muestra una tabla que ofrece un breve resumen de las funciones que se pueden utilizar. Se debe incluir la librería STDIO.H. Nombre fopen() fclose() fgets() fputs() fseek() fprintf() fscanf() feof() ferror() rewind() remove() fflush() Función Abre un archivo. Cierra un archivo. Lee una cadena de un archivo. Escribe una cadena en un archivo Busca un byte especifico de un archivo. Escribe una salida con formato en el archivo. Lee una entrada con formato desde el archivo. Devuelve cierto si se llega al final del archivo. Devuelve cierto si se produce un error. Coloca el localizador de posición del archivo al principio del mismo. Borra un archivo. Vacía un archivo. 6.2 FLUJOS Un flujo (stream) es una abstracción que se refiere a un flujo o corriente de datos que fluye entre un origen o fuente (productor) y un destino o sumidero (consumidor). Entre el origen y el destino debe existir una conexión o canal (<<pipe>>) por la que circulen los datos. La apertura de un archivo supone establecer la conexión del programa con el dispositivo que contiene al archivo, por el canal que comunica al archivo con el programa van a fluir las secuencias de datos. Hay tres flujos o canales abiertos automáticamente: extern FILE *stdin; Ing. Pablo M. Navarro Álvarez Página # 2 U.A.B.C. Facultad de Ingeniería Programación Estructurada UNIDAD VI extern FILE *stdout; extern FILE *stderr; Estas tres variables se inicializan al comenzar la ejecución del programa para admitir secuencias de caracteres, en modo texto. Su contenido es el siguiente: stein stdout stderr asocia la entrada estándar (teclado) con el programa. asocia la salida estándar (pantalla) con el programa. asocia la salida de mensajes de error (pantalla) con el programa. Así cuando se ejecuta printf("Calle Mayor 2."); se escribe en stdout, en pantalla; si se desea leer una variable entera con scanf("%d",&x); se captan los dígitos de la secuencia de entrada stdin. El acceso a los archivos se hacen con un buffer intermedio. Se puede pensar en el buffer como un array donde se van almacenando los datos dirigidos al archivo, o desde el archivo; el buffer se vuelca cuando de una forma u otra se da la orden de vaciarlo. Por ejemplo, cuando se llama a una función para leer del archivo una cadena, la función lee tantos caracteres como quepan en el buffer. A continuación se obtiene la cadena del buffer, una posterior llamada a la función obtendrá la siguiente cadena del buffer y así sucesivamente hasta que se quede vacío y se llene con una llamada posterior a la función de lectura. El lenguaje C trabaja con archivos con buffer, y está diseñado para acceder a una amplia gama de dispositivos, de tal forma que trata cada dispositivo como una secuencia, pudiendo haber secuencias de caracteres y secuencias binarias. Con las secuencias se simplifica el manejo de archivos en C. 5.3 EL PUNTERO (FILE) A UN ARCHIVO. El puntero a un archivo es el hilo común que unifica el sistema de E/S con el buffer. Un puntero a un archivo es un puntero a una información que define varias cosas sobre él, incluyendo el nombre, el estado y la posición actual del archivo. En esencia identifica un archivo específico y utiliza la secuencia asociada para dirigir el funcionamiento de las funciones de E/S con buffer. Un puntero a un archivo es una variable de tipo puntero al tipo FILE que se define en STDIO.H. Un programa necesita utilizar punteros a archivos para leer o escribir en los mismos. Para obtener una variable de este tipo se utiliza una secuencia como esta: FILE *F; Todas las funciones de estrada/salida estándar usan este puntero para conseguir información sobre el archivos abierto. Este puntero no apunta al archivo sino a una estructura que contiene información sobre él. Esta estructura incluye entre otras cosas información sobre el nombre del archivo, la dirección de la zona de memoria donde se almacena el archivo, tamaño del buffer. 5.4 APERTURA DE UN ARCHIVO Para procesar un archivo en C (y en todos los lenguajes de programación) la primera operación que hay que realizar es abrir el archivo. La apertura del archivo Ing. Pablo M. Navarro Álvarez Página # 3 U.A.B.C. Facultad de Ingeniería Programación Estructurada UNIDAD VI supone conectar el archivo externo con el programa, e indicar cómo va a ser tratado el archivo: binario, de caracteres, etc. El programa accede a los archivos a través de un puntero a la estructura FILE, la función de apertura devuelve dicho puntero. La función para abrir un archivo es fopen() y el formato de llamada es: fopen(nombre_archivo, modo); Donde nombre_archivo es un puntero a una cadena de caracteres que representan un nombre válido del archivo y puede incluir una especificación del directorio. La cadena a la que apunta modo determina como se abre el archivo. La función devuelve un puntero a FILE, a través de dicho puntero el programa hace referencia al archivo. La llamada fopen() se debe hacer de tal forma que el valor que devuelve se asigne a una variable puntero a FILE, para así después referirse a dicha variable. Ejemplo 1: El siguiente ejemplo declara una variable de tipo puntero a FILE y posteriormente se utiliza una sentencia se apertura de archivo. FILE* pf; pf = fopen(nombre_archivo, modo); A continuación se muestra una tabla conteniendo los modos permitidos para abrir un archivo así como su significado. Modo r w a rb wb ab r+ w+ a+ r+b w+b a+b Significado Abre un archivo de texto para lectura. Crea un archivo de texto para escritura. Abre un archivo de texto para añadir. Abre un archivo binario para lectura. Crea un archivo binario para escritura. Abre un archivo binario para añadir. Abre un archivo de texto para lectura / escritura. Crea un archivo de texto para lectura / escritura. Añade o crea un archivo de texto para lectura / escritura. Abre un archivo binario para lectura / escritura. Crea un archivo binario para lectura / escritura. Añade o crea un archivo binario para lectura / escritura. Como se mencionó anteriormente, la función fopen() devuelve un puntero a archivo. Un programa nunca debe alterar el valor de ese puntero. Si se produce un error cuando se esta intentando abrir un archivo, fopen() devuelve un puntero nulo. Se puede abrir un archivo bien en modo texto o binario. En la mayoría de las implementaciones, en modo texto, la secuencias de retorno de carro / salto de línea se convierten a caracteres de salto de línea en lectura. En la escritura, ocurre lo contrario: los caracteres de salto de línea se convierten en salto de línea. Estas conversiones no ocurren en archivos binarios. La macro NULL está definida en STDIO.H. Este método detecta cualquier error al abrir un archivo: como por ejemplo disco lleno o protegido contra escritura antes de comenzar a escribir en él. Ing. Pablo M. Navarro Álvarez Página # 4 U.A.B.C. Facultad de Ingeniería Programación Estructurada UNIDAD VI Ejemplo 2: En el siguiente ejemplo se abre un archivo llamado LICENCIA.EST para obtener algunos datos almacenados dentre de el y se verifica que no haya ocurrido error. #include<stdio.h> #inlcude<stdlib.h> FILE *pf; char nm[ ] = "A:\LICENCIA.EST"; pf = fopen(nm,"r"); if ( pf == NULL ) { printf("Error al abrir el archivo"); exit(1); } Ejemplo 3: En el siguiente ejemplo se abre el archivo de texto JARDINES.DAT para escribir en el los datos de un programa. Observe que en la misma línea en que se ejectura fopen() se comprueba que la operación ha sido correcta, en caso contrario termina la ejecución. #include<stdio.h> #inlcude<stdlib.h> FILE *ff; char arch[ ] = "C:\AMBIENTE\JARDINES.DAT"; if ( ( ff =fopen(arch,"w"))== NULL ) { printf("Error al abrir el archivo para escribir"); exit(1); } Si se usa fopen() para abrir un archivo para escritura, entonces cualquier archivo existente con el mismo nombre se borrará y se crea uno nuevo. Si no existe un archivo con el mismo nombre, entonces se creará. Si se quiere añadir al final del archivo entonces debe usar el modo a. Si se usa a y no existe el archivo, se devolverá un error. La apertura de un archivo para las operaciones de lectura requiere que exista el archivo. Si no existe, fopen() devolverá un error. Finalmente, si se abre un archivo para las operaciones de leer / escribir, la computadora no lo borrará si existe; sin embargo, si no existe, la computadora lo creará. 5.5 CIERRE DE UN ARCHIVO. La función fclose() cierra una secuencia que fue abierta mediante una llamada a fopen(). Escribe toda la información que todavía se encuentre en el buffer en el disco y realiza un cierre formal del archivo a nivel del sistema operativo. Un error en el cierre de Ing. Pablo M. Navarro Álvarez Página # 5 U.A.B.C. Facultad de Ingeniería Programación Estructurada UNIDAD VI una secuencia puede generar todo tipo de problemas, incluyendo la pérdida de datos, destrucción de archivos y posibles errores intermitentes en el programa. El prototipo de esta función es: int fclose(FILE *F); Donde F es el puntero al archivo devuelto por la llamada a fopen(). Si se devuelve un valor cero significa que la operación de cierre ha tenido éxito si ha habido algún error, el valor de retorno es la constante EOF. 5.6 ARCHIVOS SECUENCIALES En estos archivos, la información sólo puede leerse y escribirse empezando desde el principio del archivo. Los archivos secuenciales tienen algunas características que hay que tener en cuenta: La escritura de nuevos datos siempre se hace al final del archivo. Para leer una zona concreta del archivo hay que avanzar siempre, si la zona está antes de la zona actual de lectura, será necesario "rebobinar" el archivo. Los archivos sólo se pueden abrirse para lectura o para escritura, nunca de los dos modos a la vez. Esto es en teoría, por supuesto, en realidad C no distingue si los archivos que usamos son secuenciales o no, es el tratamiento que hagamos de ellos lo que los clasifica como de uno u otro tipo. Hay archivos que se comportan siempre como secuenciales, por ejemplo los archivos de entrada y salida estándar: stdin, stdout, stderr y stdaux. Tomemos el caso de stdin, que suele ser el teclado. Nuestro programa sólo podrá abrir ese archivos como de lectura, y sólo podrá leer los caracteres a medida que estén disponibles, y en el mismo orden en que fueron tecleados. Lo mismo se aplica para stdout y stderr, que es la pantalla, en estos casos sólo se pueden usar para escritura, y el orden en que se muestra la información es el mismo en que se envía. Un caso especial es stdaux, que suele ser el puerto serie. También es un archivo secuencial, con respecto al modo en que se leen y escriben los datos. Sin embargo se un archivos de entrada y salida. Trabajar con archivos secuenciales tiene algunos inconvenientes. Por ejemplo, imagina que tienes un archivo de este tipo en una cinta magnética. Por las características físicas de este soporte, es evidente que sólo podemos tener un archivo abierto en cada unidad de cinta. Cada archivos puede ser leído, y también sobrescrito, pero en general, los archivos que haya a continuación del que escribimos se perderán, o bien serán sobrescritos al crecer el archivo, o quedará un espacio vacío entre el final del archivo y el principio del siguiente. Lo normal cuando se quería actualizar el contenido de un archivo de cinta añadiendo o modificando datos, era abrir el archivo en modo lectura en una unidad de cinta, y crear un nuevo archivo de escritura en una unidad de cinta distinta. Los datos leídos de una cinta se editan o modifican, y se copian en la otra secuencialmente. Ing. Pablo M. Navarro Álvarez Página # 6 U.A.B.C. Facultad de Ingeniería Programación Estructurada UNIDAD VI Cuando trabajemos con archivos secuenciales en disco haremos lo mismo, pero en ese caso no necesitamos dos unidades de disco, ya que en los discos es posible abrir varios archivos simultáneamente. En cuanto a las ventajas, los archivos secuenciales son más sencillos de manejar, ya que requieren menos funciones, además son más rápidos, ya que no permiten moverse a lo largo del archivo, el punto de lectura y escritura está siempre determinado. En ocasiones pueden ser útiles, por ejemplo, cuando sólo se quiere almacenar cierta información a medida que se recibe, y no interesa analizarla en el momento. Posteriormente, otro programa puede leer esa información desde el principio y analizarla. Este es el caso de archivos "log" o "diarios" por ejemplo, los servidores de las páginas WEB pueden generar una línea de texto cada vez que alguien accede al una de las páginas y las guardan en un archivos secuencial. 5.7 ARCHIVOS DE ACCESO ALEATORIO Los archivos de acceso aleatorio son más versátiles, permiten acceder a cualquier parte del archivo en cualquier momento, como si fueran arrays en memoria. Las operaciones de lectura y/o escritura pueden hacerse en cualquier punto del archivo. En general se suelen establecer ciertas normas para la creación, aunque no todas son obligatorias: Abrir el archivo en un modo que te permita leer y escribir. Esto no es imprescindible, es posible usar archivos de acceso aleatorio sólo de lectura o sólo de escritura. Abrirlo en modo binario, ya que algunos o todos los campos de la estructura pueden no ser caracteres. Usar funciones como fread y fwrite, que permiten leer y escribir registros de longitud constante desde y hacia un archivo. Usar la función fseek para situar el puntero de lectura/escritura en el lugar apropiado de tu archivo. 5.8 FUNCIONES PARA LA LECTURA Y ESCRITURA DE CARACTERES EN ARCHIVOS Función fgetc: Esta función lee un carácter desde un archivo e incrementa la posición actual del indicador del archivo. El valor de retorno es el carácter leído como un unsigned char convertido a int. Si no hay ningún carácter disponible, el valor de retorno es EOF. El parámetro es un puntero a una estructura FILE del archivo del que se hará la lectura. Sintáxis: int fgetc(FILE *fichero); Función fputc: Esta función escribe un carácter a un fichero. El valor de retorno es el carácter escrito, si la operación fue completada con éxito, en caso contrario será EOF. Los Ing. Pablo M. Navarro Álvarez Página # 7 U.A.B.C. Facultad de Ingeniería Programación Estructurada UNIDAD VI parámetros de entrada son el carácter a escribir, convertido a int y un puntero a una estructura FILE del fichero en el que se hará la escritura. Sintáxis: int fputc(int caracter, FILE *fichero); Función feof: Esta función sirve para comprobar si se ha alcanzado el final del archivo. Frecuentemente deberemos trabajar con todos los valores almacenados en un archivo de forma secuencial, la forma que suelen tener los bucles para leer todos los datos de un archivo es permanecer leyendo mientras no se detecte el fin del archivo. La función feof suele usarse como prueba para verificar si se ha alcanzado o no ese punto. Su prototipo se encuentra en STDIO.H. Devuelve cierto si se ha alcanzado el final del archivo, en cualquier otro caso, 0. Por supuesto, se puede aplicar este método a archivos de texto también. Sintaxis: int feof(FILE *fichero); Ejemplo: En el siguiente ejemplo se lee un archivo de texto llamado (origen.txt) caracter por caracter y se muestra su contenido en la pantalla. Observe el manejo de fopen, fclose y feof en el ejemplo. #include <stdio.h> #include <stdlib.h> main() { FILE *archivo; char letra; archivo = fopen("origen.txt","r"); if (archivo == NULL) { printf( "No se puede abrir el archivo.\n" ); exit( 1 ); } printf( "Contenido del Archivo:\n" ); letra = fgetc(archivo); while (feof(archivo) == 0) { printf( "%c",letra ); letra = fgetc(archivo); } } if (fclose(archivo)!= 0) printf( "Problemas al cerrar el archivo\n" ); Ejemplo: En el siguiente ejemplo vamos a completar ahora la parte que faltaba en la ejemplo anterior: escribir en un archivo. En este ejemplo, abrimos un archivo de Ing. Pablo M. Navarro Álvarez Página # 8 U.A.B.C. Facultad de Ingeniería Programación Estructurada UNIDAD VI texto llamado origen.txt y lo copiamos en otro llamado destino.txt. Además, el archivo se muestra en pantalla. #include <stdio.h> #include <stdlib.h> main() { FILE *origen, *destino; char letra; origen = fopen("origen.txt","r"); destino= fopen("destino.txt","w"); if (origen == NULL || destino == NULL) { printf( "Problemas con la apertura de los archivos.\n" ); exit( 1 ); } letra = fgetc(origen); while (!feof(origen)) { fputc(letra, destino); printf( "%c",letra ); letra = fgetc(origen); } } if (fclose(origen)!= 0) printf( "Problemas al cerrar el archivos origen.txt\n" ); if (fclose(destino)!= 0) printf( "Problemas al cerrar el archivos destino.txt\n" ); En los ejemplos anteriores, cuando entramos en el bucle while para la lectura del archivo, ésta se realiza hasta que se encuentre el final del archivo. La detección del final del archivo se puede llevar a cabo de dos formas: con la función feof comprobando si el valor de letra es EOF (el último carácter de cualquier archivo). En los ejemplos se ha usado la función feof. Esta función es de la forma: int feof(FILE *fichero); Esta función comprueba si se ha llegado al final del archivo, en cuyo caso, como se mencionó anteriormente devuelve un valor distinto de 0, en caso contrario si llegó al final del archivo devuelve un cero. Por eso lo usamos del siguiente modo: while ( feof(fichero) == 0 ) while ( !feof(fichero) ) Ing. Pablo M. Navarro Álvarez Página # 9 U.A.B.C. Facultad de Ingeniería Programación Estructurada UNIDAD VI La segunda forma consiste en comprobar si el carácter leído es el de fin de fichero EOF: while ( letra != EOF ) Sin embargo, cuando trabajamos con archivos de texto no hay ningún problema, pero si estamos manejando un archivo binario podemos encontrarnos EOF antes del fin de archivo. Por eso es preferible usar feof. 5.9 FUNCIONES PARA LA LECTURA Y ESCRITURA DE CADENAS EN ARCHIVOS Función fgets: Esta función está diseñada para leer cadenas de caracteres. Leerá hasta n-1 caracteres o hasta que lea un retorno de línea. En este último caso, el carácter de retorno de línea también es leído. El parámetro n nos permite limitar la lectura para evitar desbordar el espacio disponible en la cadena. El valor de retorno es un puntero a la cadena leída, si se leyó con éxito, y es NULL si se detecta el final del archivo o si hay un error. Los parámetros son: la cadena a leer, el número de caracteres máximo a leer y un puntero a una estructura FILE del archivo del que se leerá. Sintáxis: char *fgets(char *cadena, int n, FILE *fichero); Función fputs: La función fputs escribe una cadena en un archivo. No se añade el carácter de retorno de línea ni el carácter nulo final. El valor de retorno es un número no negativo o EOF en caso de error. Los parámetros de entrada son la cadena a escribir y un puntero a la estructura FILE del archivo donde se realizará la escritura. Sintáxis: int fputs(const char *cadena, FILE *stream); Ejemplo: En el siguiente ejemplo, se muestra como hacer la lectura de una cadena que tiene una longitud de 100 caracteres. El ejemplo supone la existencia previa del archivo origen.txt que contiene la información que se leerá. Se resaltaron en negrita las instrucciones nuevas para manejo de cadenas en archivos. #include <stdio.h> #include <stdlib.h> main() { FILE *archivo; char texto[100]; Ing. Pablo M. Navarro Álvarez Página # 10 U.A.B.C. Facultad de Ingeniería Programación Estructurada UNIDAD VI fichero = fopen("origen.txt","r"); if (archivo == NULL) { printf( "No se puede abrir el archivo.\n" ); exit( 0 ); } printf( "Contenido del archivo:\n" ); fgets(texto,100,archivo); while (feof(archivo) == 0) { printf( "%s",texto ); fgets(texto,100,archivo); } } if (fclose(archivo)!=0) printf( "Problemas al cerrar el archivo\n" ); Ejemplo: El siguiente ejemplo, muestra como realizar la escritura de una cadena en un archivo y luego muestra el contenido del archivo a través de la lectura del mismo. #include <stdio.h> #include <stdlib.h> main() { FILE *archivo; char texto[100]; archivo = fopen("destino.txt","w"); if (archivo == NULL) { printf( "No se puede crear el archivo.\n" ); exit( 1 ); } /* Escribe en el archivo */ fputs("Esta es la primera línea del archivo\n", archivo); fputs("Esta es la segunda línea del archivo\n", archivo); fputs("Esta es la última línea del archivo\n", archivo); if (fclose(archivo)!=0) printf( "Problemas al cerrar el archivo\n" ); /* Se abre el archivo de nuevo para leerlo y mostrar su contenido */ archivo = fopen("destino.txt","r"); if (archivo == NULL) { Ing. Pablo M. Navarro Álvarez Página # 11 U.A.B.C. Facultad de Ingeniería Programación Estructurada UNIDAD VI } printf( "No se puede crear el archivo.\n" ); exit( 1 ); printf( "Contenido del archivo:\n" ); fgets(texto,100,archivo); while (feof(archivo) == 0) { printf( "%s",texto ); fgets(texto,100,archivo); } } if (fclose(archivo)!=0) printf( "Problemas al cerrar el archivo\n" ); 5.10 FUNCIONES PARA LA LECTURA Y ESCRITURA EN REGISTROS DE LONGITUD FIJA Función fread: Esta función está pensada para trabajar con registros de longitud constante. Es capaz de leer desde un archivo uno o varios registros de la misma longitud y a partir de una dirección de memoria determinada. El usuario es responsable de asegurarse de que hay espacio suficiente para contener la información leída. El valor de retorno es el número de registros leídos, no el número de bytes. Los parámetros son: un puntero a la zona de memoria donde se almacenarán los datos leídos, el tamaño de cada registro, el número de registros a leer y un puntero a la estructura FILE del fichero del que se hará la lectura. Sintáxis: size_t fread(void *puntero, size_t tamaño, size_t nregistros, FILE *fichero); Función fwrite: Esta función también está pensada para trabajar con registros de longitud constante y forma pareja con fread. Es capaz de escribir hacia un archivo uno o varios registros de la misma longitud almacenados a partir de una dirección de memoria determinada. El valor de retorno es el número de registros escritos, no el número de bytes. Los parámetros son: un puntero a la zona de memoria donde se almacenarán los datos leídos, el tamaño de cada registro, el número de registros a leer y un puntero a la estructura FILE del fichero del que se hará la lectura. Sintáxis: size_t fwrite(void *puntero, size_t tamaño, size_t nregistros, FILE *fichero); Ing. Pablo M. Navarro Álvarez Página # 12 U.A.B.C. Facultad de Ingeniería Programación Estructurada UNIDAD VI 5.11 FUNCIONES 'C' ESPECÍFICAS PARA ARCHIVOS DE ACCESO ALEATORIO Función fseek: Esta función sirve para situar el cursor del archivo para leer o escribir en el lugar deseado. El valor de retorno es cero si la función tuvo éxito, y un valor distinto de cero si hubo algún error. Los parámetros de entrada son: un puntero a una estructura FILE del fichero en el que queremos cambiar el cursor de lectura/escritura, el valor del desplazamiento y el punto de origen desde el que se calculará el desplazamiento. El parámetro origen puede tener tres posibles valores: SEEK_SET: el desplazamiento se cuenta desde el principio del fichero. El primer byte del fichero tiene un desplazamiento cero. SEEK_CUR: el desplazamiento se cuenta desde la posición actual del cursor. SEEK_END: el desplazamiento se cuenta desde el final del fichero. Sintaxis: int fseek(FILE *fichero, long int desplazamiento, int origen); Función ftell: La función ftell sirve para averiguar la posición actual del cursor de lectura/escritura de un archivo. El valor de retorno será esa posición, o -1 si hay algún error. El parámetro de entrada es un puntero a una estructura FILE del fichero del que queremos leer la posición del cursor de lectura/escritura. Sintaxis: long int ftell(FILE *fichero); Ing. Pablo M. Navarro Álvarez Página # 13