Documentação atualizada.
Ao MetaTrader 5 Android adicionada a apresentação do histórico de negociação na forma de posições. Anteriormente na aba "Histórico" eram exibidas apenas transações e ordens a partir do histórico, e agora é possível analisar as negociações usando posições. Para fazer isso, todas as operações relacionadas com a posição são agrupadas num único registro, nele é possível ver:
Foi adicionada a apresentação do histórico na forma de posições. Anteriormente, na aba "Histórico" eram exibidas apenas as transações a partir do histórico, agora nela também são apresentadas as posições. A plataforma de negociação recolhe dados sobre operações - relativas à posição - e agrupa estes dados numa única entrada. Nela pode ser visto:
//+------------------------------------------------------------------+ //| Função de modelo | //+------------------------------------------------------------------+ template<typename T1,typename T2> string Assign(T1 &var1,T2 var2) { var1=(T1)var2; return(__FUNCSIG__); } //+------------------------------------------------------------------+ //| Sobrecarga especial para o caso bool+string | //+------------------------------------------------------------------+ string Assign(bool &var1,string var2) { var1=(StringCompare(var2,"true",false) || StringToInteger(var2)!=0); return(__FUNCSIG__); } //+------------------------------------------------------------------+ //| Script program start function | //+------------------------------------------------------------------+ void OnStart() { int i; bool b; Print(Assign(i,"test")); Print(Assign(b,"test")); }Como resultado da execução deste código, podemos ver que para o par int+string foi utilizada a função de modelo Assign(), enquanto, na segunda chamada, para o par bool+string já foi utilizada a versão sobrecarregada.
string Assign<int,string>(int&,string) string Assign(bool&,string)
template<typename T> T Func() { return (T)0; } void OnInit() { Func<double>(); // especialização explícita da função de modelo }Assim, a especialização não se realiza através do parâmetro de chamada, mas sim especificando os tipos.
Documentação atualizada.
Documentação atualizada.
Foi adicionada a possibilidade de login e registro da conta
MQL5.com via Facebook. Agora, se você tem um perfil, nesta rede social,
você pode em alguns cliques acessar os bate-papos e todo o conjunto de
serviços para MetaTrader 5.
#resource caminho_para_o_arquivo_do_recurso as tipo_de_variável_de_recurso nome_de_variável_de_recurso
#resource "data.bin" as int ExtData[] // declaração de matriz de tipo numérico, que contém dados a partir do arquivo data.bin #resource "data.bin" as MqlRates ExtData[] // declaração de matriz de estrutura simples, que contém dados a partir do arquivo data.bin #resource "data.txt" as string ExtCode // declaração de cadeias de caracteres, que contém dados a partir do arquivo data.txt #resource "data.txt" as string ExtCode[] // declaração de matriz de sequência de caracteres, que contém dados a partir do arquivo data.txt #resource "image.bmp" as bitmap ExtBitmap[] // declaração de matriz unidimensional, que contém em si a varredura a partir do arquivo BMP, tamanho da matriz = height * width #resource "image.bmp" as bitmap ExtBitmap2[][] // declaração de matriz bidimensional, que contém em si a varredura a partir do arquivo BMP, tamanho da matriz [height][width]
Documentação atualizada.
string str; ... if(str) // aparecerá o erro de compilação "Cannot convert type 'string' to 'bool'" (nas compilações anteriores não acontecia o erro) Print("str is true");É necessário escrever uma condição explícita:
string str; ... //--- verifica se a cadeia de caracteres é inicializada if(str!=NULL) Print("str is true"); ou //--- verifica se o valor da cadeia de caracteres é "true" if(StringCompare(str,"true",false)) Print("str is true"); ou //--- verifica se a cadeia de caracteres é um número e não é igual a zero if((int)str!=0) Print("str is true");
Correções de crash-logs.
void ArrayPrint( const void& array[], // matriz de saída uint digits=_Digits, // número de casas decimais const string separator=NULL, // delimitador entre os valores dos campos de estrutura ulong start=0, // índice do primeiro elemento de saída ulong count=WHOLE_ARRAY, // número de elementos de saída ulong flags=ARRAYPRINT_HEADER|ARRAYPRINT_INDEX|ARRAYPRINT_LIMIT|ARRAYPRINT_ALIGN );ArrayPrint não exibe, no registro, todos os campos da matriz de estruturas, uma vez que os campos tanto de matriz como de ponteiros de objetos são omitidos. Para exibição de todos os campos dessa estrutura, será necessário escrever a função de saída em massa com a formatação desejada.
//--- exibe os valores das 10 últimas barras MqlRates rates[]; if(CopyRates(_Symbol,_Period,1,10,rates)) { ArrayPrint(rates); Print("Verificação\n[time]\t[open]\t[high]\t[low]\t[close]\t[tick_volume]\t[spread]\t[real_volume]"); for(int i=0;i<10;i++) { PrintFormat("[%d]\t%s\t%G\t%G\t%G\t%G\t%G\t%G\t%I64d\t",i, TimeToString(rates[i].time,TIME_DATE|TIME_MINUTES|TIME_SECONDS), rates[i].open,rates[i].high,rates[i].low,rates[i].close, rates[i].tick_volume,rates[i].spread,rates[i].real_volume); } } else PrintFormat("CopyRates failed, error code=%d",GetLastError()); //--- exemplo de saída /* [time] [open] [high] [low] [close] [tick_volume] [spread] [real_volume] [0] 2016.11.09 04:00:00 1.11242 1.12314 1.11187 1.12295 18110 10 17300175000 [1] 2016.11.09 05:00:00 1.12296 1.12825 1.11930 1.12747 17829 9 15632176000 [2] 2016.11.09 06:00:00 1.12747 1.12991 1.12586 1.12744 13458 10 9593492000 [3] 2016.11.09 07:00:00 1.12743 1.12763 1.11988 1.12194 15362 9 12352245000 [4] 2016.11.09 08:00:00 1.12194 1.12262 1.11058 1.11172 16833 9 12961333000 [5] 2016.11.09 09:00:00 1.11173 1.11348 1.10803 1.11052 15933 8 10720384000 [6] 2016.11.09 10:00:00 1.11052 1.11065 1.10289 1.10528 11888 9 8084811000 [7] 2016.11.09 11:00:00 1.10512 1.11041 1.10472 1.10915 7284 10 5087113000 [8] 2016.11.09 12:00:00 1.10915 1.11079 1.10892 1.10904 8710 9 6769629000 [9] 2016.11.09 13:00:00 1.10904 1.10913 1.10223 1.10263 8956 7 7192138000 Verificação [time] [open] [high] [low] [close] [tick_volume] [spread] [real_volume] [0] 2016.11.09 04:00:00 1.11242 1.12314 1.11187 1.12295 18110 10 17300175000 [1] 2016.11.09 05:00:00 1.12296 1.12825 1.1193 1.12747 17829 9 15632176000 [2] 2016.11.09 06:00:00 1.12747 1.12991 1.12586 1.12744 13458 10 9593492000 [3] 2016.11.09 07:00:00 1.12743 1.12763 1.11988 1.12194 15362 9 12352245000 [4] 2016.11.09 08:00:00 1.12194 1.12262 1.11058 1.11172 16833 9 12961333000 [5] 2016.11.09 09:00:00 1.11173 1.11348 1.10803 1.11052 15933 8 10720384000 [6] 2016.11.09 10:00:00 1.11052 1.11065 1.10289 1.10528 11888 9 8084811000 [7] 2016.11.09 11:00:00 1.10512 1.11041 1.10472 1.10915 7284 10 5087113000 [8] 2016.11.09 12:00:00 1.10915 1.11079 1.10892 1.10904 8710 9 6769629000 [9] 2016.11.09 13:00:00 1.10904 1.10913 1.10223 1.10263 8956 7 7192138000 */
void OnStart() { int arr[]; //--- quanta memória é usada inicialmente Print("Array size:",ArraySize(arr)," Memory used:",MQLInfoInteger(MQL_MEMORY_USED)," MB"); //--- quanta memória é usado para uma matriz de tamanho 1, mas com uma reserva de ArrayResize(arr,1,1024*1024); Print("Array size:",ArraySize(arr)," Memory used:",MQLInfoInteger(MQL_MEMORY_USED)," MB"); //--- após aumentar a matriz, o tamanho da memória utilizada não é alterado pela reserva ArrayResize(arr,1024*512,1024*1024); Print("Array size:",ArraySize(arr)," Memory used:",MQLInfoInteger(MQL_MEMORY_USED)," MB"); //--- após reduzir a matriz, o tamanho da memória utilizada também não é alterado ArrayResize(arr,1); Print("Array size:",ArraySize(arr)," Memory used:",MQLInfoInteger(MQL_MEMORY_USED)," MB"); //--- a memória sem uso é liberada pela remoção da reserva ArrayResize(arr,1,-1); Print("Array size:",ArraySize(arr)," Memory used:",MQLInfoInteger(MQL_MEMORY_USED)," MB"); }
#include <Graphics/Graphic.mqh> double Func1(double x) { return MathPow(x,2); } double Func2(double x) { return MathPow(x,3); } double Func3(double x) { return MathPow(x,4); } void OnStart() { GraphPlot(Func1,Func2,Func3,-2,2,0.05,CURVE_LINES); }Resultado:
#include <Math/Stat/Binomial.mqh> #include <Graphics/Graphic.mqh> void OnStart(void) { double vars[101]; double results[101]; const int N=2000; //--- MathSequence(0,N,20,vars); MathProbabilityDensityBinomial(vars,N,M_PI/10,true,results); ArrayPrint(results,4); GraphPlot(results); //--- }Resultado:
Documentação atualizada.
Na biblioteca padrão, foi incluía a versão MQL5 da biblioteca de análise numérica ALGLIB.
Possibilidades da biblioteca
Como usar
Os arquivos da biblioteca ALGLIB estão localizados no diretório \MQL5\Include\Math\Alglib. Para usar as funções, adicione o arquivo principal da biblioteca ao seu programa:
A biblioteca padrão foram adicionadas funções de trabalho com estatística matemática. Agora, em MQL5, estão disponíveis as possibilidades da linguagem R, ela é um dos melhores instrumentos de processamento estatístico e análise de dados.<br1>
Possibilidades da biblioteca
A biblioteca estatística contém funções para cálculo de características estatísticas de dados, bem como funções para trabalhar com distribuições estatísticas:
Como usar
Os arquivos da biblioteca ALGLIB estão localizados no diretório \MQL5\Include\Math\Stat. Para usar as funções, adicione o arquivo com as funções desejadas ao seu programa, por exemplo:
#include <Math\Stat\Binomal.mqh> #include <Math\Stat\Cauchy.mqh>
Leia descrições detalhadas das funções da biblioteca no artigo Distribuições estatísticas em MQL5: pegamos as melhores a partir de R.
Na biblioteca padrão, foi incluía a versão MQL5 da biblioteca Fuzzy, ela implementa sistemas de inferência de lógica difusa Mastop e Sugeno.
Possibilidades da biblioteca
Como usar
Os arquivos da biblioteca Fuzzy estão localizados no diretório \MQL5\Include\Math\Fuzzy. Para usar as funções, adicione o arquivo com as funções desejadas ao seu programa, por exemplo:
#include <Math\Fuzzy\mamdanifuzzysystem.mqh> #include <Math\Fuzzy\sugenofuzzysystem.mqh>
Uma descrição detalhada da biblioteca pode ser encontrada ni Code Base: Fuzzy, biblioteca para trabalhar com lógica difusa
long FileLoad( const string filename, // [in] nome do arquivo void &buffer[], // [out] matriz na qual é tomado em consideração o arquivo uint common_flag=0 // [in] 0 - busca do arquivo na pasta Files do terminal, FILE_COMMON - na pasta comum dos terminais ); bool FileSave( const string filename, // [in] nome do arquivo const void &buffer[], // [in] matriz armazenada no arquivo uint common_flag=0 // [in] 0 - criação do arquivo na pasta Files do terminal, FILE_COMMON - na pasta comum dos terminais );Exemplo de como armazenar, numa pasta, uma matriz de ticks e, em seguida, lê-la.
//--- parâmetros de entrada input int ticks_to_save=1000; // número de ticks //+------------------------------------------------------------------+ //| Script program start function | //+------------------------------------------------------------------+ void OnStart() { string filename=_Symbol+"_ticks.bin"; MqlTick ticks[]; //--- int copied=CopyTicks(_Symbol,ticks,COPY_TICKS_ALL,0,ticks_to_save); if(copied!=-1) { PrintFormat(" CopyTicks(%s) copied %d ticks",_Symbol,copied); //--- se o histórico de ticks estiver sincronizado, o código de erro será igual a zero if(!GetLastError()==0) PrintFormat("%s: Ticks are not synchronized. Error=",_Symbol,copied,_LastError); //--- armazenamos os ticks no arquivo if(!FileSave(filename,ticks,FILE_COMMON)) PrintFormat("FileSave() failed, error=%d",GetLastError()); } else PrintFormat("Failed CopyTicks(%s), Error=",_Symbol,GetLastError()); //--- agora lemos de volta estes ticks a partir do arquivo ArrayFree(ticks); long count=FileLoad(filename,ticks,FILE_COMMON); if(count!=-1) { Print("Time\tBid\tAsk\tLast\tVolume\tms\tflags"); for(int i=0;i<count;i++) { PrintFormat("%s.%03I64u:\t%G\t%G\t%G\t%I64u\t0x%04x", TimeToString(ticks[i].time,TIME_DATE|TIME_SECONDS),ticks[i].time_msc%1000, ticks[i].bid,ticks[i].ask,ticks[i].last,ticks[i].volume,ticks[i].flags); } } }
//--- velas pintadas na mesma cor #property indicator_label1 "One color candles" #property indicator_type1 DRAW_CANDLES //--- foi indicado apenas uma cor, por isso todas as velas terão apenas uma cor #property indicator_color1 clrGreenSe forem indicadas duas cores, os contornos das velas serão desenhadas usando a primeira cor, enquanto o corpo usando a segunda.
//--- a cor das velas difere da cor das sombras #property indicator_label1 "Two color candles" #property indicator_type1 DRAW_CANDLES //--- sombras e contorno de velas de cor verde, corpo de cor branca #property indicator_color1 clrGreen,clrWhiteSe forem indicadas duas cores, os contornos das velas serão desenhadas usando a primeira cor, enquanto o as velas de alta e baixa serão definidas usando uma segunda e terceira.
//--- o cor das velas é diferente da cor das sombras #property indicator_label1 "One color candles" #property indicator_type1 DRAW_CANDLES //--- as sombras e contornos de cor verde; o corpo da vela de alta de cor branca; corpo da vela de baixa de cor vermelha #property indicator_color1 clrGreen,clrWhite,clrRedAssim, usando o estilo DRAW_CANDLES, é possível criar suas próprias opções personalizadas para colorir velas. Também é possível alterar dinamicamente todas as cores -no processo de trabalho do indicador- mediante a função PlotIndexSetInteger(índice_de_construção_DRAW_CANDLES, PLOT_LINE_COLOR, número_de_modificador, cor), aqui o número_de_modificador pode ter os seguintes valores:
//--- definimos a cor do contorno e das sombras PlotIndexSetInteger(0,PLOT_LINE_COLOR,0,clrBlue); //--- definimos a cor do corpo para a vela de alta PlotIndexSetInteger(0,PLOT_LINE_COLOR,1,clrGreen); //--- definimos a cor do corpo para a vela de baixa PlotIndexSetInteger(0,PLOT_LINE_COLOR,2,clrRed);
Documentação atualizada.
class CFoo final { //--- corpo da classe }; class CBar : public CFoo { //--- тело класса };Ao tentar herdar a partir da classe com o modificador final, como foi mostrado no exemplo acima, o compilador exibirá o erro:
class CFoo { void virtual func(int x) const { } };Além disso, o método é substituído na classe herdada:
class CBar : public CFoo { void func(short x) { } };No entanto, de acordo com o erro, o tipo de argumento é alterado de int para short. De fato, neste caso, não acontece uma substituição, senão uma sobrecarga do método. Após agir segundo o algoritmo para determinar a função sobrecarregada, em determinadas situações, o compilador pode selecionar o método definido na classe base, em vez do método substituído.
class CBar : public CFoo { void func(short x) override { } };Se, durante a substituição, for alterada a assinatura do método, o compilador não poderá encontrar, na classe pai, o método com exatamente a mesma assinatura e exibirá o erro de compilação:
class CFoo { void virtual func(int x) final { } }; class CBar : public CFoo { void func(int) { } };Ao tentar substituir o método com o modificador final, como foi mostrado no exemplo acima, o compilador exibirá o erro:
Documentação atualizada.
class CFoo { }; class CBar { }; //+------------------------------------------------------------------+ //| Script program start function | //+------------------------------------------------------------------+ void OnStart() { void *vptr[2]; vptr[0]=new CFoo(); vptr[1]=new CBar(); //--- for(int i=0;i<ArraySize(vptr);i++) { if(dynamic_cast<CFoo *>(vptr[i])!=NULL) Print("CFoo * object at index ",i); if(dynamic_cast<CBar *>(vptr[i])!=NULL) Print("CBar * object at index ",i); } CFoo *fptr=vptr[1]; // emitirá o erro de apresentação de ponteiros, vptr[1] não é um objeto CFoo } //+------------------------------------------------------------------+
string text="Hello"; ushort symb=text[0]; // retorna o código do símbolo 'H'
Documentação atualizada.