Mira cómo descargar robots gratis
¡Búscanos en Telegram!
Pon "Me gusta" y sigue las noticias
¿Es interesante este script?
Deje un enlace a él, ¡qué los demás también lo valoren!
¿Le ha gustado el script?
Evalúe su trabajo en el terminal MetaTrader 5
Visualizaciones:
145
Ranking:
(3)
Publicado:
\MQL5\Scripts\
GZIP_test.mq5 (3.05 KB) ver
\MQL5\Include\
GZIP.mqh (8.89 KB) ver
MQL5 Freelance ¿Necesita un robot o indicador basado en este código? Solicítelo en la bolsa freelance Pasar a la bolsa

La biblioteca permite descifrar archivos GZIP de ficheros *.gz o respuestas de sitios comprimidos con este formato. Probado en archivos con hasta 0.5 GB de texto comprimido en ellos.

La librería puede comprobar automáticamente por la bandera en el 4º byte si el archivo es un fichero comprimido o datos comprimidos del sitio, en el segundo caso no hay nombre de fichero en los datos.

Los datos de entrada para la descompresión deben representarse en un array de tipo char.

Para la descompresión se utiliza la función terminal CryptDecode(CRYPT_ARCH_ZIP, tmp, key, tx);

La clase GZIP contiene métodos

isGZIP(char& gz[])

- comprueba los tres primeros caracteres de los datos recibidos para ver si están comprimidos en formato GZIP.

Tras esta comprobación, se puede llamar a una de las sobrecargas del método unGZIP:

bool unGZIP(char& gz[], char& tx[], string& fname, bool printTime=false){}

el caso de uso preferido en términos de velocidad y consumo de memoria. Durante la descompresión, se llena el array char tx. A continuación, los datos de la misma pueden ser procesados por CSV o JSON parser. De esta manera obtenemos el resultado sin pegar el array en una cadena y luego dividirlo por cadenas u otros caracteres.

Si aún así necesitas obtener una cadena, puedes utilizar una de las sobrecargas:

bool unGZIP(char& gz[], string& out, bool printTime=false, uint codepage=CP_ACP){}

devolver true si el desempaquetado se ha realizado correctamente, la cadena desempaquetada está en la cadena out

o

string unGZIP(char& gz[], bool printTime=false, uint codepage=CP_ACP){}

devolver cadena. Si el desempaquetado falla, la cadena estará vacía.

Se debe tener cuidado al utilizar la concatenación de datos en una sola cadena.
Si desempaquetas un archivo con 0,5GB de datos, la cadena requerirá otros 0,5GB, luego puedes dividirla en una matriz de cadenas, lo que requerirá otros 0,5GB. Más el coste de tiempo de todas estas operaciones.

Ejemplo de caso de uso para leer datos comprimidos de un sitio web y luego leer de un archivo: (este script se adjunta para su descarga)

#property copyright "Copyright 2023, Forester"
#property link      "https://www.mql5.com"
#property version   "1.00"

#include <GZIP.mqh>
GZIP gzip;

void OnStart(){
      Print("GZipped webpage read sample:");
      string url="https://............";
      char out[]; 
      if(http_req(url, out,"GET","Accept-Encoding: gzip, deflate\r\n", 1,0)){
          if(gzip.isGZIP(out)){
            Print("GZIP detected");
            string txt; if(!gzip.unGZIP(out, txt, 1, CP_UTF8)){return;}//CP_ACP
            Print(txt);
         }else{
         Print("No GZIP");Print(CharArrayToString(out, 0, WHOLE_ARRAY, CP_UTF8));
         }
      }
      
      Print("File read sample:");
      bool is_common=1;
      string fn="3.csv.gz";
      bool is_zip=1;

      int h;
      if(is_zip){
         h = FileOpen(fn,FILE_READ|FILE_BIN|FILE_READ|(is_common?FILE_COMMON:0));
      }else{
         h = FileOpen(fn,FILE_READ|FILE_CSV|FILE_ANSI|(is_common?FILE_COMMON:0));
      }
      if( h!=INVALID_HANDLE){
         Print ("Start gzip");
         char gz[],tx[];
         FileReadArray(h, gz); FileClose(h); 
         
         if(gzip.isGZIP(gz)){
            Print("GZIP detected");
            string fname;
            if(!gzip.unGZIP(gz, tx,fname,1)){return;}
            //string txt; if(!unGZIP(gz, txt, 1, CP_ACP)){return;}//CP_UTF8
            //string txt=unGZIP(gz, 1, CP_ACP);if(txt==""){return;}
            if(fname!=NULL){Print("File name: ",fname,", file size: ",ArraySize(tx));}
            string t=  CharArrayToString(tx,0,100);Print("Filr content: ",t);t=  CharArrayToString(tx,ArraySize(tx)-100,100);Print("... ",t);

 
            //ulong mcs = GetMicrosecondCount();
            //string csvRow[];int columns=0, next=0; char sep=',', newLine='\n';
            //while(getCSVRow(tx, csvRow, columns, next, sep, newLine) && !IsStopped()){//obtener siguiente fila
              // for(int c=0; c<columnas; c++){
               //Imprimir();
              // }
               //Imprimir(siguiente);
            //}
            //Print("Tiempo de análisis CSV: ",(GetMicrosecondCount()-mcs)," mcs");
            //ArrayPrint(csvRow);

        }else{}
      }
}

int getCSVRow(char& csv[], string& outAr[], int& cols, int& next, char& sep, char& newLine){//obtener la siguiente fila
   for(int i=next; i<ArraySize(csv); i++){
      if(csv[i] == newLine){
         cols=StringSplit(CharArrayToString(csv,next,i-next),sep,outAr);// procesa 1 línea por separado - 5-10% más rápido que parseCSV y e tiene memoria para 1 array grande.
         next=i+1;
         return true;
      }
   }
   return false;
}



bool http_req(string url, char& out[],string method="GET",string headers_request=NULL, bool printTime=false,bool debug=false){
   ulong mcs = (printTime?GetMicrosecondCount():0);
   bool retVal=false;
   ResetLastError();
   char data[];string headers=NULL;
   int r=WebRequest(method, url, headers_request, 5000, data, out, headers);
   if(r==-1){Print("Error in WebRequest. Err code =",GetLastError());MessageBox("It is necessary to add the address '"+url+"' to the list of allowed URLs in the 'Advisors' tab","Error",MB_ICONINFORMATION);}
   else{if(r==200){ retVal=  true; }else{PrintFormat("Download error '%s', responce code %d",url,r);Print("Error in WebRequest. Err code =",GetLastError());}}if(debug){PrintFormat("Responce headers: %s\r\nResponce:",headers);Print(CharArrayToString(out));}//
   if(printTime){Print("WebRequest time: ",(GetMicrosecondCount()-mcs)," mcs");}
   return retVal;
}

Este ejemplo lee un fichero de la carpeta files, y lo descomprime en un array.
Se imprimen los 100 primeros y últimos caracteres del archivo descomprimido.
El array puede ser enviado a un analizador CSV o JSON. Para JSON existe la librería JASON en kodobase. Puede analizar los datos recibidos como una matriz de caracteres.

Ejemplo de salida al descomprimir un archivo CSV comprimido de 120 MB, el archivo fuente es de 463 MB:

2025.05.12 15:08:40.510    GZipped webpage read sample:
2025.05.12 15:08:41.319    WebRequest time: 809637 mcs
2025.05.12 15:08:41.319    GZIP detected
2025.05.12 15:08:41.319    UnGZIP time: 3 mcs
2025.05.12 15:08:41.319    {"retCode":0,"retMsg":"OK","result":{"category":"linear","list":[... Юя
2025.05.12 15:08:41.319    File read sample:
2025.05.12 15:08:41.320    Start gzip
2025.05.12 15:08:41.384    GZIP detected
2025.05.12 15:08:42.582    UnGZIP time: 1198136 mcs
2025.05.12 15:08:42.593    File name: BTCUSD2025-05-09.csv, file size: 486006135
2025.05.12 15:08:42.593    Filr content: timestamp,symbol,side,size,price,tickDirection,trdMatchID,grossValue,homeNotional,foreignNotional,RP
2025.05.12 15:08:42.593    ... 36.00,ZeroPlusTick,e92fbea7-1471-591e-95f7-4dc0edde771c,971.4774228646926,1,9.714774228646926e-06,0

El desempaquetado tardó unos 1,2 segundos.


Traducción del ruso realizada por MetaQuotes Ltd
Artículo original: https://www.mql5.com/ru/code/59309

ADX Indicator (MQL5) ADX Indicator (MQL5)

El indicador ADX (Average Directional Index) suavizado mejora el ADX estándar aplicando filtros de suavizado exponencial dobles para reducir el ruido y proporcionar señales de tendencia más claras. Traza tres líneas: +DI suavizado (azul), -DI (rojo) y la línea principal del ADX (verde). Esta versión refinada ayuda a los operadores a identificar la fuerza de la tendencia y los posibles cambios de dirección con menos señales falsas. El indicador destaca a la hora de confirmar tendencias establecidas y advertir del debilitamiento del impulso antes de que se produzcan cambios reales en el precio, lo que lo hace valioso tanto para las estrategias de seguimiento de tendencias como para determinar los puntos óptimos de entrada/salida.

Divergence Awesome Ocilator Divergence Awesome Ocilator

Este indicador personalizado MQL5 detecta divergencias entre la acción del precio y el Awesome Oscillator (AO), señalando posibles retrocesos o continuaciones del mercado. Traza flechas de compra/venta en el gráfico, muestra el AO como un histograma y dibuja líneas de tendencia para resaltar las divergencias.

AutoCloseOnProfitLoss Expert - Automatically Close All Positions on Profit/Loss AutoCloseOnProfitLoss Expert - Automatically Close All Positions on Profit/Loss

El Asesor Experto (EA) AutoCloseOnProfitLoss es una potente herramienta de automatización para MetaTrader 5, diseñada para cerrar todas las posiciones abiertas cuando se alcanzan los objetivos de beneficios o pérdidas predefinidos.

Swaps Monitor for a Single Symbol Swaps Monitor for a Single Symbol

Una sencilla utilidad para supervisar los swaps largos y cortos de un mismo símbolo. Si los swaps de su agente de bolsa se especifican en puntos en lugar de en la divisa de la cuenta, esta utilidad convierte automáticamente los puntos en la divisa de la cuenta. Los swaps se triplican los miércoles. La alineación horizontal y vertical puede ajustarse en las entradas.