- Métodos de almacenamiento de la información: texto y binario
- Escritura y lectura de archivos en modo simplificado
- Abrir y cerrar archivos
- Gestión de descriptores de archivo
- Seleccionar una codificación para el modo texto
- Escritura y lectura de arrays
- Escritura y lectura de estructuras (archivos binarios)
- Escritura y lectura de variables (archivos binarios)
- Escritura y lectura de variables (archivos de texto)
- Gestión de la posición en un expediente
- Obtención de las propiedades de un archivo
- Forzar escritura de caché en disco
- Eliminación de un archivo y comprobación de su existencia
- Copia y desplazamiento de archivos
- Búsqueda de archivos y carpetas
- Trabajar con carpetas
- Cuadro de diálogo de selección de archivos o carpetas
Obtención de las propiedades de un archivo
En el proceso de trabajo con archivos, además de escribir y leer datos directamente, a menudo es necesario analizar sus propiedades. Una de las principales propiedades, el tamaño del archivo, puede obtenerse utilizando la función FileSize. Pero hay algunas características más que pueden solicitarse utilizando FileGetInteger.
Tenga en cuenta que la función FileSize requiere un gestor de archivo abierto. FileGetInteger tiene algunas propiedades, incluido el tamaño, que pueden reconocerse por el nombre del archivo, y no es necesario abrirlo primero.
ulong FileSize(int handle)
La función devuelve el tamaño de un archivo abierto por su descriptor. En caso de error, el resultado es igual a 0, que es un tamaño válido para la ejecución normal de la función, por lo que siempre debe analizar los posibles errores utilizando _LastError (o GetLastError).
El tamaño del archivo también puede obtenerse desplazando el puntero al final del archivo FileSeek(handle, 0, SEEK_END) y llamando a FileTell(handle). Estas dos funciones se describen en la sección anterior.
long FileGetInteger(int handle, ENUM_FILE_PROPERTY_INTEGER property)
long FileGetInteger(const string filename, ENUM_FILE_PROPERTY_INTEGER property, bool common = false)
La función tiene dos opciones: trabajar a través de un descriptor de archivo abierto, y por el nombre del archivo (incluyendo uno cerrado).
La función devuelve una de las propiedades de archivo especificadas en el parámetro property. La lista de propiedades válidas es diferente para cada una de las opciones (véase más abajo). Aunque el tipo de valor es long, dependiendo de la propiedad solicitada, puede contener no sólo un número entero sino también datetime o bool: realice la conversión de tipos requerida explícitamente.
Cuando solicite una propiedad por el nombre del archivo puede utilizar de forma adicional el parámetro common para especificar en qué carpeta debe buscarse el archivo: la carpeta actual del terminal MQL5/Files (false, por defecto) o la carpeta común Users/<user_name>...MetaQuotes/Terminal/Common/Files (true). Si el programa MQL se está ejecutando en el probador, el directorio de trabajo se encuentra dentro de la carpeta del agente de pruebas (Tester/<agent>/MQL5/Files), véase la introducción del capítulo Trabajar con archivos.
La siguiente tabla enumera todos los miembros de ENUM_FILE_PROPERTY_INTEGER.
Propiedad |
Descripción |
---|---|
FILE_EXISTS * |
Comprobación de existencia (similar a FileIsExist) |
FILE_CREATE_DATE * |
Fecha de creación |
FILE_MODIFY_DATE * |
Fecha de la última modificación |
FILE_ACCESS_DATE * |
Fecha de último acceso |
FILE_SIZE * |
Tamaño del archivo en bytes (similar a FileSize) |
FILE_POSITION |
Posición del puntero en el archivo (similar a FileTell) |
FILE_END |
Posición al final del archivo (similar a FileIsEnding) |
FILE_LINE_END |
Posición al final de una cadena (similar a FileIsLineEnding) |
FILE_IS_COMMON |
Archivo abierto en la carpeta compartida de terminales (FILE_COMMON) |
FILE_IS_TEXT |
Archivo abierto como texto (FILE_TXT) |
FILE_IS_BINARY |
Archivo abierto como binario (FILE_BIN) |
FILE_IS_CSV |
Archivo abierto como CSV (FILE_CSV) |
FILE_IS_ANSI |
Archivo abierto como ANSI (FILE_ANSI) |
FILE_IS_READABLE |
Archivo abierto para lectura (FILE_READ) |
FILE_IS_WRITABLE |
Archivo abierto para escritura (FILE_WRITE) |
Las propiedades cuyo uso está permitido por nombre de archivo están marcadas con un asterisco. Si intenta obtener otras propiedades, la segunda versión de la función devolverá un error 4003 (INVALID_PARAMETER).
Algunas propiedades pueden cambiar mientras se trabaja con un archivo abierto: FILE_MODIFY_DATE, FILE_ACCESS_DATE, FILE_SIZE, FILE_POSITION, FILE_END, FILE_LINE_END (sólo para archivos de texto).
En caso de error, el resultado de la llamada es -1.
La segunda versión de la función permite comprobar si el nombre especificado es el nombre de un archivo o directorio. Si se especifica un directorio al obtener propiedades por nombre, la función establecerá un código de error interno especial 5018 (ERR_MQL_FILE_IS_DIRECTORY), mientras que el valor devuelto será correcto.
Probaremos las funciones de esta sección utilizando el script FileProperties.mq5. Funcionará en un archivo con un nombre predefinido.
const string fileprop = "MQL5Book/fileprop"; |
Al principio de OnStart, vamos a intentar solicitar el tamaño mediante un descriptor erróneo (no se recibió a través de la llamada a File Open). Después de FileSize se requiere la comprobación de la variable _LastError, y FileGetInteger devuelve inmediatamente un valor especial, un indicador de error (-1).
void OnStart()
|
A continuación, creamos un nuevo archivo o abrimos un archivo existente y lo reiniciamos, y luego escribimos el texto de prueba.
handle = PRTF(FileOpen(fileprop, FILE_TXT | FILE_WRITE | FILE_ANSI)); // 1
|
Solicitamos selectivamente algunas de las propiedades.
PRTF(FileGetInteger(fileprop, FILE_SIZE)); // 0, not written to the disk yet
|
La información sobre la longitud del archivo por su descriptor tiene en cuenta el búfer de caché actual, y por el nombre del archivo, la longitud real estará disponible sólo después de que se cierre el archivo, o si se llama a la función FileFlush (véase la sección Forzar escritura de caché en disco).
La función devuelve fechas y horas como el número de segundos de la época estándar desde el 1 de enero de 1970, que corresponde al tipo datetime y puede ser llevada a él.
La solicitud de banderas de apertura de archivos (su modo) tiene éxito para la versión de la función con un descriptor; en concreto, recibimos una respuesta que el archivo es de texto y no binario. Sin embargo, la siguiente petición similar de un nombre de archivo fallará porque la propiedad sólo se admite cuando se pasa un manejador válido. Esto ocurre aunque el nombre apunte al mismo archivo que hemos abierto.
PRTF(FileGetInteger(fileprop, FILE_IS_TEXT)); // -1 / INVALID_PARAMETER(4003) |
Esperemos un segundo, cerremos el archivo y volvamos a comprobar la fecha de modificación (esta vez por el nombre, ya que el descriptor ya no es válido).
Sleep(1000);
|
Aquí puedes ver claramente que el tiempo ha aumentado en 1.
Por último, asegúrese de que las propiedades están disponibles para los directorios (carpetas).
PRTF((datetime)FileGetInteger("MQL5Book", FILE_CREATE_DATE));
|
Dado que todos los ejemplos del libro se encuentran en la carpeta «MQL5Book», esta ya debe existir. Sin embargo, su tiempo de creación real será diferente. El código de error FILE_IS_DIRECTORY en este caso nos lo muestra la macro PRTF. En el programa de trabajo, la llamada a la función debe realizarse sin macro y, a continuación, debe leerse el código en _LastError.