==== Lenguaje C: Entrada y salida ==== * [[pub:c_io#e_s_estandar|Entrada y salida estándar]] * Salida con formato: printf() * Entrada de datos con formato: scanf() * Entrada de caracteres: getchar() * Salida de caracteres: putchar() * Entrada y salida de cadenas * [[pub:c_io#ficheros_y_secuencias|Ficheros y secuencias]] * Apertura y cierre de un fichero * Fin de fichero * Entrada y salida de texto * Entrada y salida de caracteres * Entrada y salida de cadenas * Lectura y escritura de datos binarios * Entrada y salida con formato * Entrada y salida mediante acceso directo * Otras operaciones sobre ficheros ---- === E/S estándar === Las //entradas y salidas// de información de un programa pueden realizarse: * Sobre las __unidades de almacenamiento__ * //Apertura// del archivo * Operación de //lectura/escritura// sobre el archivo * //Cierre// del archivo * Sobre __dispositivos periféricos__ * //Directamente// sobre los periféricos: operación hardware * A través de los //controladores// de los periféricos * Con los recursos ofrecidos por el //sistema operativo// Cuando un programa está en //ejecución//, se convierte en un **proceso** que dispone de: * Un **canal estándar de entrada** asociado por defecto al teclado: **''sdtin'' ** * Lo que el usuario escribe en el teclado va a parar al canal ''stdin'' * Un **canal estándar de salida** asociado por defecto a la pantalla: **''stdout'' ** * Lo que el proceso escribe en el canal ''stdout'' va a parar a la pantalla * Un **canal estándar para salida de errores** asociado por defecto a la pantalla: **''stderr'' ** * Lo que el proceso escribe en el canal ''stderr'' también va a parar a la pantalla El estándar ANSI C creó un **conjunto de funciones** estándar para la entrada y salida a través de los ficheros estándar ''stdin'' y ''stdout'' * Están definidas en el archivo ''stdio.h'', por lo que para utilizarlas en un programa es preciso incluir la línea: #include Las más importantes son: * ''printf()'' para **escribir** datos **con formato** * ''scanf()'' para **leer** datos **con formato** * ''getchar()'' para **leer** caracteres del **teclado** * ''putchar()'' para **escribir** caracteres en **pantalla** == Salida con formato: printf() == La función devuelve el número de bytes escritos o ''EOF'' en caso de error * Plantilla de utilización: printf("cadena_de_control", lista_de_argumentos); * Elementos en la "cadena_de_control" : * Caracteres y símbolos ASCII normales * Caracteres de //escape// o **secuencias de barra invertida** * Comienzan siempre con símbolo <<''''>> * **Especificadores de formato** para la representación de los valores almacenados en variables * Comienzan siempre con el símbolo <<''%''>> * La "lista_de_argumentos" es una relación de las variables (separadas por comas) cuyos contenidos se quiere mostrar * Tiene que haber al menos tantas variables como especificadores de formato * Caracteres de escape o secuencias de barra invertida más habituales: |''\a'' |Alarma (pitido)|''\'''|Comilla simple | |''\b'' |Espacio atrás |''\"'' |Comillas dobles| |''\f'' |Salto de página|''\\'' |Barra invertida| |''\n'' |Nueva línea |''\oo'' |Carácter ASCII en octal| |''\r'' |Retorno de línea|''\xHH'' |Carácter ASCII en hexadecimal| |''\t'' |Tabulador|''\0'' |Carácter nulo (Código ASCII cero)| * Sintaxis de los especificadores de formato: %[flags][anchura][.precision][prefijo-tipo] formato * ''flags'': Opcional: * ''-'' justifica a la izquierda * ''+'' fuerza la aparición del signo siempre * ''0'' completa con ceros a la izquierda todo el campo * ''anchura'': Opcional: Ancho del campo en el que aparecerá el dato * ''.precision'': Opcional: * En enteros, número de dígitos * En reales, número de dígitos decimales * En cadenas, número de caracteres * ''prefijo-tipo'': Opcional, para indicar a la función como debe interpretar el dato contenido en la memoria: * ''h'' interpreta un ''short'' * ''l'' interpreta ''long'' en los enteros o ''double'' en los reales * ''L'' interpreta un ''long double'' * ''formato'': Obligatorio, para determinar el tipo de dato de la variable cuyo contenido se va a mostrar: * ''d'' Entero con signo en mostrado en decimal * ''u'' Entero sin signo mostrado en decimal * ''o'' Entero sin signo mostrado en octal * ''x'' Entero sin signo mostrado en hexadecimal * ''f'' Número real en formato ''[–]ddd.ddd'' * ''e'' Número real en formato ''[–]d.dddE[±]ddd'' * ''g'' Número real en el formato más corto * ''c'' Carácter * ''s'' Cadena de caracteres * Ejemplos printf("Número entero: %d", edad); printf("Letra:%c t Octal:%o t Hexadecimal: %x",codigo, codigo, codigo); printf("Número real: %f t %E t %G", estatura, estatura, estatura); == Entrada con formato: scanf() == La función devuelve el número de datos leídos correctamente o EOF en caso de error * Plantilla de utilización: scanf("cadena_de_control", lista_de_argumentos); * Elementos de la ''cadena_de_control'' : * No es una cadena que aparezca en pantalla * Se corresponde con la cadena que la función espera encontrarse en el teclado carácter a carácter * Incluye los caracteres de separación o //espacios en blanco// que separan los especificadores de formato. Pueden ser * El espacio en blanco ''“ ”'' * El tabulador ''t'' * El retorno de carro ''n'' * Incluye los **especificadores de formato** que provocan la captura de un dato * Sintaxis de los especificadores de formato %[*][anchura][prefijo-tipo] formato * ''[*]'': Opcional: anula la asignación al siguiente dato scanf("%d %*s”, &valor); /* Lee el dato y la cadena que se teclee a continuación del valor entero, pero no se asigna a ninguna variable */ * ''anchura'': Opcional: Número de caracteres a leer (se ignoran los restantes) * ''prefijo-tipo'': Opcional: * En enteros, número de dígitos * En reales, número de dígitos decimales * En cadenas, número de caracteres * ''formato'': Obligatorio, determina el tipo de dato (igual que en ''printf()'') * La lista de argumentos es una relación de las //direcciones de memoria// de las variables (separadas por comas) * La dirección de una variable se obtiene precediendo el nombre de la variable del operador <<''&''>> * Debe haber el mismo número de variables que especificadores de formato El **buffer de teclado** es una zona de almacenamiento intermedio asociada a la entrada estándar ''stdin'' * Se almacenan los códigos ASCII de las teclas pulsadas * Se valida cuando se pulsa la tecla INTRO * Sólo se eliminan del buffer los códigos de los caracteres leídos * Es la zona de memoria donde ''scanf()'' obtiene los valores * Puede que no se cojan todos los caracteres tecleados * Se quedan hasta la siguiente lectura del buffer del teclado * Hay una función definida en ''stdio.h'' que borra este buffer fflush(sdtin); == Entrada de caracteres: getchar() == Función para leer caracteres del teclado. Prototipo: int getchar(void); * Definida en ''stdio.h'' * No requiere ningún argumento * Devuelve el código ASCII de la tecla pulsada o EOF en caso de error * Solo finaliza, cogiendo un código, cuando se pulsa la tecla INTRO * Si se ha pulsado más de una tecla, quedan en el buffer del teclado * Ejemplo: char a; a = getchar(void); scanf("%c", &a); * * Las dos sentencias son equivalentes * Las teclas especiales (F1…F12) y las combinaciones con CTRL y ALT generan dos códigos de 8 bits, es decir, equivalen a dos pulsaciones (dos caracteres) == Salida de caracteres: putchar() == Función para mostrar caracteres en la pantalla. Prototipo: int putchar(int variable); * Definida en ''stdio.h'' * Como argumento requiere el nombre de la //variable// que contiene el código a mostrar * Devuelve en un entero el código ASCII del carácter mostrado o EOF en caso de error * Ejemplo: char a; putchar((int)a); printf("%c", a); * * Las dos sentencias son equivalentes === Lectura y escritura de cadenas === En lenguaje C no existe un tipo de dato de //cadena de caracteres//, los arrays de caracteres o //cadenas de caracteres// son vectores: * Cuyos elementos se almacenan consecutivamente en memoria * Se puede hacer referencia a todo el conjunto mediante un único identificador * Para referenciar a un elemento se utiliza el identificador y un índice entre corchetes cadena[indice] * El último elemento es __siempre__ el carácter nulo ''0'' * Declaración de un array (incluido el nulo final): char nombrevariable[NUMERO_DE_ELEMENTOS]; * Se tratarán con detalle más adelante == Lectura de cadenas: gets( ) == gets(char *cadena); * Definida en ''stdio.h'' * Necesita, como argumento, el identificador de una cadena de caracteres * Lee todos los caracteres tecleados hasta el INTRO que lo recoge y lo sustituye por '0' en memoria * Ejemplo: #define NUM_ELEM 100 char cadena[NUM_ELEM]; /* Declaración */ gets(cadena); /* Lee una cadena */ scanf("%s", cadena); /* Lee una cadena */ * Las dos sentencias son equivalentes * Leen todo lo tecleado (sea cual sea el valor de ''NUM_ELEM'') == Escritura de cadenas: puts( ) == puts(cadena); * Definida en ''stdio.h'' * Necesita, como argumento, el identificador de una cadena de caracteres o la propia cadena entre comillas dobles * Lleva a pantalla los símbolos ASCII de los códigos almacenados hasta encontrar el nulo '0' que es sustituido por un INTRO * Ejemplo: puts(cadena) /* Muestra una cadena */ printf("%s", cadena); /* Muestra una cadena */ * Las dos sentencias son equivalentes * La función ''printf()'' puede utilizarse para mostrar en pantalla la cadena que va entre comillas como argumento === Ficheros y secuencias === El lenguaje C proporciona mecanismos para la entrada y salida por ficheros: * Que no dependen del dispositivo físico sobre el que actúen * Son funciones genéricas, potentes y flexibles * Distingue dos tipos de elementos * Ficheros * Secuencias o //streams// * **fichero**: Dispositivo físico y real sobre el que se realizan las operaciones de entrada o salida * **secuencia** (**stream**): Ente abstracto sobre el que se realiza una operación de entrada o salida genérica * Las secuencias, en muchas ocasiones, se asocian a dispositivos físicos o a ficheros: * La secuencia de salida estándar se asocia a la pantalla * La secuencia de entrada estándar se asocia al teclado * El concepto de **fichero** puede aplicarse, además de a ficheros en disco, a impresoras, terminales, controladores, etc. * El concepto de **secuencia** puede entenderse como un buffer de datos o un dispositivo lógico que proporciona un camino para los datos en las operaciones de entrada o salida * Cuando se __abre un fichero__ para operaciones de entrada y/o salida, se le __asocia una secuencia__, un camino que permitirá la transferencia de información entre ese fichero y el programa. * El lenguaje C contempla los ficheros como secuencias continuas de bytes que pueden ser accedidos de forma individual: * Todas las funciones de E/S sirven para todas las secuencias, sólo hay que redirigirlas al fichero deseado {{:pub:c_io1.png?500}} * El sistema operativo (DOS/Windows) admite que un fichero pueda ser abierto de dos modos: * En modo texto: Los bytes de la secuencia son códigos ASCII * En modo binario: Los bytes de la secuencia son códigos binarios de 8 bits * En los sistemas Unix y Linux no existe tal distinción * No hay ninguna indicación añadida al modo de apertura de un fichero En //**modo texto**// el __final de la línea__ se representa: * En lenguaje C: como <<''n''>> (En ASCII CR: Retorno de carro, código 10) * En el sistema operativo Windows: como la sucesión de los códigos ASCII: ''CR+LR'' (Retorno de carro + Salto de línea, códigos 10 y 13) * Las funciones de lectura en lenguaje C al encontrar la secuencia ''CR+LF'', la convierten a <<''n''>> * Las funciones de lectura al encontrar el código correspondiente a ''Ctrl+D'' (''Ctrl+Z'' en Windows) lo interpretan como ''EOF'' (End Of File\, fin de fichero). * Ejemplo: Si en un fichero de texto del DOS (*.TXT) escribimos: En un lugar de la mancha, de cuyo nombre no quiero acordarme. * Al leer el fichero en //**modo binario**// desde un programa en lenguaje C se obtendrá la siguiente secencia: En un lugar de la mancha, r\nde cuyo nombre no quiero acordarme.EOF * Si se abre en //**modo texto**// , lo que se recogerá será lo siguiente: En un lugar de la mancha, nde cuyo nombre no quiero acordarme.EOF Al ejecutar un programa en modo consola, automáticamente el sistema operativo abre tres secuencias estándar: * ''stdin'' * **Entrada estándar**. Se asocia al teclado * ''stdout'' * **Salida estándar**. Se asocia a la pantalla * ''stderr'' * **Salida estándar de errores**. Se asocia a la pantalla * Las secuencias estándar tienen asociado un buffer de memoria física cada una * Las E/S por consola operan igual que las E/S por ficheros, pero redirigen la operación real sobre las secuencias estándar ''stdin'', ''stdout'' y ''stderr'' == Apertura y cierre de un fichero == Para **acceder** a los ficheros se precisa un __descriptor del fichero__ (//puntero// de tipo ''FILE'') * Declaración: FILE *puntero; * ''FILE'' es una constante definida en ''stdio.h'' * El descriptor apunta a un **buffer** que contiene toda la información necesaria para operar con el fichero * Se utiliza para hacer referencia al fichero en todas las operaciones sobre este * Debe declararse antes de utilizarse * El descriptor se //inicializa// al //abrir//__sin error__ un fichero al que se le hace apuntar Antes de cualquier operación sobre un fichero es preciso **abrir** el fichero, utilizando la función ''fopen()'' * Declaración: FILE * fopen(char *nombrearchivo, char *modo); * Devuelve: * Un descriptor de tipo ''FILE'' que apunta al fichero abierto * Un descriptor nulo (''NULL'') en caso de error * Recibe dos cadenas de caracteres: * La primera con el nombre del fichero (con la ruta de acceso) * La segunda con el modo de apertura que se selecciona |**Modos de apertura de ficheros** | | | | |**Modo** |**Texto** |**Binario** |**Observaciones** | |Abrir para leer|''%%"r"%%'' |''%%"rb"%%'' |Si no existe, se produce error| |Crear para escribir|''%%"w"%%'' |''%%"wb"%%'' |Si existe, se pierde el contenido| |Abrir o crear para añadir|''%%"a"%%'' |''%%"ab"%%'' |Si no existe, se crea| |Abrir para leer y/o escribir|''%%"r+"%%'' |''%%"rb+"%%'' |Debe existir| |Crear para leer y/o escribir|''%%"w+"%%'' |''%%"wb+"%%'' |Si existe, se pierde el contenido| |Abrir o crear para añadir y/o leer|''%%"a+"%%'' |''%%"ab+"%%'' |Si no existe, se crea| **Mientras el fichero esté abierto**, el descriptor correspondiente apunta a una __estructura__ que contiene toda la información necesaria sobre el fichero: * Nombre, tamaño, atributos, posición del apuntador para lecturas y/o escritura, etc. Al **finalizar un programa** que utiliza ficheros: * __Si termina normalmente__, los ficheros que estuviesen abiertos son **cerrados** por el sistema operativo. * Un fichero __no cerrado correctamente__ queda **inutilizado** y la información que pudiera contener se pierde y queda inaccesible. En previsión de finalizaciones anómalas, __tras las operaciones de lectura y/o escritura__, es preciso **cerrar los ficheros**, utilizando la función ''fclose()'': * Declaración int fclose(FILE *descriptor); * Devuelve * un entero de valor cero si el cierre ha sido correcto * EOF en caso de error * Recibe como argumento el descriptor al fichero que se quiere cerrar * Ejemplo de apertura y cierre de un fichero: FILE *pf; /* descriptor a fichero */ if ((pf=fopen("misdatos/prueba.x","w+")) == NULL) { puts("nNo es posible crear el fichero"); exit(0); } else printf("nEl fichero se ha abierto"); /* Tras realizar todas las operaciones necesarias, es preciso cerrar el fichero antes de finalizar el programa */ fclose(pf); /* El fichero ha quedado cerrado */ El **carácter de fin de fichero** está representado por la constante simbólica ''EOF'', definida en ''stdio.h'' * Es el //último byte// del fichero * Cuando se leen bytes del fichero (con ''fgetc()'') puede leerse el EOF y no distinguirse como último carácter, especialmente cuando se trata de secuencias binarias * La función ''feof()'', declarada en ''stdio.h'' devuelve un valor distinto de cero (verdadero/true) cuando se lee el byte de fin de fichero (''EOF'') while (!feof(puntfile)) { /* Operaciones sobre el fichero abierto */ } == Entrada y salida de texto == Las funciones de lectura y escritura de **caracteres** en ficheros están definidas en ''stdio.h'' int fgetc( FILE *pf); * Lee un carácter en el fichero cuyo descriptor recibe * Devuelve el carácter leído en un entero o ''EOF'' en caso de error int fputc( int car, FILE *pf); * Escribe un carácter en el fichero cuyo descriptor recibe * Devuelve ''EOF'' en caso de error * Recibe como argumentos: * ''car'': El carácter a escribir * ''pf'': El descriptor al fichero * Ejemplos de lectura y escritura de un carácter en un fichero: FILE *pf1, *pf2; char letra; pf1 = fopen("leer.txt", "r"); letra = fgetc(pf1); /* Lee un carácter */ pf2 = fopen ("escribir.txt", "w"); fputc(letra, pf2); /* Escribe un carácter */ fclose(pf1); fclose(pf2); Las funciones de lectura y escritura de cadenas de texto en ficheros están definidas en ''stdio.h'' char * fgets(char *cad, int numcar, FILE *pf); * Devuelve un puntero a la cadena leída o un puntero nulo en caso de error * Recibe como argumentos * ''cad'': Un puntero a la zona de memoria donde se almacenará la cadena * ''numcar-1'': Es el número de caracteres a leer. Será añadido el carácter nulo * ''pf'': El puntero al fichero * Si encuentra un carácter de fin de línea (''n''), éste será el último carácter leído int fputs(char *puntcad, FILE *pf); * Devuelve en un entero el último carácter escrito o ''EOF'' en caso de error * Recibe como argumentos * ''puntcad'': Un puntero a cadena que se quiere escribir * ''pf'': El puntero al fichero * Ejemplos de lectura y escritura de una cadena de caracteres en un fichero: FILE *pf1, *pf2; char lect[50]; char escr[]="Mensaje a guardar en el fichero"; int num=50-1; pf1 = fopen("leer.txt", "r"); fgets(lect, num, pf1); /* Lee una cadena de 49 caracteres de leer.txt */ pf2 = fopen ("escribir.txt", "w"); fputs(escr, pf2); /* Escribe la cadena "Mensaje a guardar en el fichero escribir.txt */ fclose(pf1); fclose(pf2); == Lectura y escritura de datos binarios == Para la **lectura de un conjunto de datos**: unsigned fread(void *buf, unsigned numbytes, unsigned numdat, FILE *pf); Para la **escritura de un conjunto de datos**: unsigned fwrite(void *buf, unsigned numbytes, unsigned numdat, FILE *pf); * Devuelven el número de datos leídos o escritos * Reciben * ''buf'': Un puntero a los datos que son leídos o escritos * ''numbytes'': representa el número de bytes de que consta cada uno de los datos a a leer o escribir (se obtiene con ''sizeof()'') * ''numdat'': representa el número total de datos, items o elementos a leer o escribir * ''pf'': es el descriptor al fichero sobre el que van a leer o escribir * Mediante el manejo de datos binarios, el contenido de los ficheros puede ser similar al contenido de las variables en memoria * Es importante cuando se trabaja con estructuras y uniones * Las funciones ''fread'' y ''fwrite'' pertenecen al ANSI C y están definidas en ''stdio.h'' * Ejemplo de lectura y escritura de datos binarios: FILE *pf; float valor1=3.5, valor2; pf=fopen ("archivo.dat", "ab+"); /* "a+" en Unix */ fwrite(&valor1, sizeof(valor), 1, pf); /* Escribe */ fread(&valor2, sizeof(float), 1, pf); /* Lee */ == Entrada y salida por ficheros con formato == * Las funciones ''fprintf()'' y ''fscanf()'' son idénticas a ''printf()'' y ''scanf()'' respectivamente, pero operan sobre un descriptor. También están declaradas en ''stdio.h'' int fprintf(FILE *pf, const char* cad_control, lista_argumentos); int fscanf(FILE *pf, const char* cad_control, lista_argumentos); * Argumentos que reciben: * ''pf'': Representa un puntero al fichero sobre el que opera la función * ''cad_control'': Es la cadena en la que s e incluyen los especificadores de formato y sus modificadores * ''lista_argumentos'': Representa la lista de argumentos que se corresponden con los especificadores de formato de la cadena de control (lista de variables cuyos contenidos quieren escribirse o leerse sobre el fichero) * Devuelven: * ''fprintf()'' devuelve en un entero el número de bytes escritos * ''fscanf()'' devuelve en un entero el número de campos correctamente escaneados y almacenados o EOF en caso de error. * La llamada: fprintf(stdout, "Número: %d", num); * es equivalente a la llamada: printf("Número: %d", num); * Cuando se escribe en un fichero mediante la función ''fprintf(pf, …)'' el contenido del fichero es similar al mostrado en pantalla con la función ''fprintf(stdout, …)'' * Ejemplo de escritura y lectura con formato: FILE *pf; int i = 100; char c = 'C'; float f = 1.234; pf = fopen("prueba.dat", "w+"); fprintf(pf, "%d %c %f", i, c, f); /* Escribe en el fichero */ fscanf(pf, "%d %c %f", &i, &c, &f); /* Lee los mismos datos en el fichero */ fclose(pf); == Entrada y salida mediante acceso directo == El acceso a los ficheros puede hacerse: * En **modo secuencial**: los datos son leídos o escritos seguidos, sin saltos * En **modo aleatorio**: es posible acceder a cualquier posición para realizar una operación de lectura o de escritura Los punteros de tipo ''FILE'' apuntan a una estructura creada por el sistema operativo que controla las operaciones sobre ese fichero. * La estructura incluye un puntero de lectura-escritura que determina la posición actual en la que se va a escribir o a leer en cada momento * Al abrir un fichero, el puntero de lectura-escritura apunta al comienzo del fichero (salvo se si abre para añadir) La función ''fseek()'', definida en ''stdio.h'', permite el movimiento aleatorio por el fichero abierto estableciendo una nueva posición para el apuntador de lectura-escritura: int fseek(FILE *pf, long nbytes, int origen); * Devuelve un valor verdadero si el movimiento se realizó con éxito o cero en caso contrario * Recibe * ''pf'': Descriptor con el que se opera * ''nbytes'': Número de bytes que queremos desplazar el apuntador de lectura-escritura del fichero con relación al punto de partida * ''origen'': Representa el punto que se toma como origen o referencia. Se utilizan constantes simbólicas definidas en ''stdio.h'': * ''SEEK_SET'' corresponde al principio del fichero * ''SEEK_CUR'' corresponde a la posición actual * ''SEEK_END'' corresponde al final del fichero * Ejemplo: #define N 5 /* Será la fila 5 */ int matriz[20][4], *punt; /* 20 filas y 4 columnas*/ FILE *pf; punt = matriz; /* Apertura del fichero sin errores */ fwrite(punt, sizeof(int), 20*4, pf); /* Escribe la matriz en un fichero */ fseek(pf, sizeof(int)*4*N, SEEK_SET); /* Apunta a los datos de la fila N, al ser 4*sizeof(int) el tamaño de una fila */ fread(&matriz[N][0], sizeof(int), 4, pf); /* Lee los datos de la fila N */ == Otras operaciones sobre ficheros == ---- * Función ''ftell()'' long ftell(FILE *pf); * * Devuelve un entero largo con la posición del apuntador de lectura-esritura del fichero con respecto al principio del fichero. * Recibe el puntero a un fichero abierto * Está definida en ''stdio.h'' ---- * Función ''rewind()'' void rewind(FILE *pf); * * Inicializa el indicador de posición o apuntador de lectura-escritura haciendo que apunte al principio del fichero * No devuelve nada * Recibe el puntero a un fichero abierto * Está definida en ''stdio.h'' ---- * Función ''remove()'' int remove(char *nombre_archivo); * * Borra el fichero cuyo nombre se especifique en la cadena que recibe como argumento * Devuelve cero si la operación tuvo éxito y ''-1'' si se produce algún error * En caso de error, la variable global ''errno'', definida en ''errno.h'' indicará el tipo de error * Está definida en ''stdio.h'' ---- * Función ''fflush()'' int fflush(FILE *pf); * * Vacía los bufferes de entrada/salida asociados al flujo descrito por ''pf'' * Devuelve cero si la operación tuvo éxito y NULL si se produce algún error * Está definida en ''stdio.h'' * Es muy utilizada para borrar el buffer del teclado y cuando se trabaja con impresoras ---- * Función ''tmpfile()'' FILE * tmpfile(void)); * * Crea un fichero temporal que es borrado automáticamente cuando el fichero es cerrado o al terminar el programa * El fichero temporal se crea en modo ''"w+"'' * Devuelve un descriptor al fichero temporal creado o un puntero nulo si no se puede crear * Está definida en ''stdio.h'' ---- \\