A partir disto, você pode encontrar toda a cadeia.
Olhamos para o comentário aberto e, se houver de #XXX, significa que ele foi fechado parcialmente - procure pelo bilhete XXX do comentário e procure-o na história. Olhe lá comentário - se houver de#YYYY - significa que também foi parcialmente fechado antes - olhe bilhete YYY de comentário e procure-o na história. Veja o comentário - se houver de#ZZZZ - significa que também foi parcialmente fechado antes - repita a busca. Se não há nenhum de#..., então é o primeiro de toda a cadeia.
A partir disto, você pode encontrar toda a cadeia.
Olhamos para o comentário aberto e, se houver de #XXX, significa que anteriormente estava parcialmente fechado - procure pelo bilhete XXX do comentário e procure-o na história. Olhe lá comentário - se houver de#YYYY - significa que também foi parcialmente fechado antes - olhe bilhete YYY de comentário e procure-o na história. Veja o comentário - se houver de#ZZZZ - significa que também foi parcialmente fechado antes - repita a busca. Se não há nenhum de#..., então é o primeiro de toda a cadeia.
Obrigado, pode haver uma ordem na direção oposta, que eu também cortarei. Tenho medo de ficar confuso. Eu acho que seria mais fácil usar a ordem de lucro de uma determinada data, é claro, se formos capazes de descobrir quando a posição foi aberta, porque a data muda quando a posição é parcialmente fechada
A partir disto, você pode encontrar toda a cadeia.
Veja comentário aberto e se houver de #XXX, significa que foi parcialmente fechado antes - procure o bilhete XXX a partir de comentário e procure-o na história. Veja o comentário lá - se houver de#YYYY - então também foi parcialmente fechado antes - veja o bilhete YYY a partir do comentário e procure por ele na história. Veja o comentário - se houver de#ZZZZ - significa que também foi parcialmente fechado antes - repita a busca. Se não há nenhum de#..., então é o primeiro de toda a cadeia.
Artem você sabe que este nem sempre é o caso. E para não traçar uma corrente para não interrogar o terminal três vezes - a história é conduzida, mesmo assim, em matrizes e estruturas próprias. Não é diferente de manter seu próprio banco de dados, exceto pelas etapas extras
O terminal e seu API é o nível mais baixo possível. E para implementar a lógica do robô, é lógico fazer a contabilidade em seus termos (comércio, cadeia, grupo, transação - todos a chamam de forma diferente). É apenas sensato mantê-lo separado e não tentar reconstruí-lo a cada espirro (tick/bar).
Você sabe que este nem sempre é o caso, Artyom. E assim, não é preciso perguntar três vezes ao terminal ao rastrear a cadeia - a história ainda é conduzida para suas próprias matrizes e estruturas. Não é diferente de manter seu próprio banco de dados, exceto pelas etapas extras
O terminal e seu API é o nível mais baixo possível. E para a realização da lógica robótica, é lógico manter a contabilidade em seus termos (comércio, cadeia, grupo, transação - todos a chamam de forma diferente). É apenas sensato mantê-lo separado e não tentar reconstruí-lo a cada espirro (tick/bar).
Há muito tempo eu tenho tudo feito - não leio a história todas as vezes - mas está sempre atualizado, e posso encontrar tudo o que preciso lá com facilidade e muito rapidamente. Mas para aconselhar alguém a fazer o mesmo, eu preciso de pelo menos alguns artigos. E assim escrevi a lógica de encontrar a cadeia inteira.
Obrigado, pode haver uma ordem na direção oposta que eu também triturarei. Tenho medo de ficar confuso. Eu acho que seria mais fácil usar a função Lucro para fechar uma posição a partir de uma determinada data, é claro, se você puder descobrir quando a posição foi aberta, porque em um fechamento parcial a data muda
Para buscar uma cadeia, basta conhecer o ticket da ordem, a cadeia inteira da qual você quer saber - passe o ticket como parâmetro para a função de busca, e a saída - uma matriz preenchida ou uma matriz de estruturas com todos os dados de cada ordem da cadeia inteira.
Eu nem sei aproximadamente o que você acabou de dizer.
Pelo menos me dê um exemplo de como deveria ser.
Eu resolvo o problema da seguinte maneira: busca de correntes pela história. Bem, para que a história esteja inequivocamente disponível, eu utilizo duas variantes:
Se sem DLL, então na descrição do programa em 24 negrito )))) especifico que o histórico da conta deve ser sempre carregado por completo (guia Histórico da conta da janela Terminal, menu de contexto - Todo Histórico).
Com DLL - Expert Advisor mantém a guia "Account history" atualizada, independentemente de qualquer ação do usuário.
Funções para determinar a ordem pai, se a ordem atual não for a principal:
int GetSignOfPartialOrCloseByClose()
{
string comment = OrderComment();
if (comment == "")
return0;
// Ордер образовался вследствии частичного закрытияint fromStart = StringFind(comment, "from #");
if (fromStart >= 0)
return GetTicketByPartialClose(comment, fromStart, OrderType(), OrderOpenTime());
// Ордер образовался вследствии встречного закрытияif (StringFind(comment, "partial close") >= 0)
{
datetime openTime = OrderOpenTime();
int type = OrderType();
for (int i = OrdersHistoryTotal() - 1; i >= 0; i--)
{
if (!OrderSelect(i, SELECT_BY_POS, MODE_HISTORY))
continue;
if (OrderOpenTime() != openTime)
continue;
if (OrderType() != type)
continue;
if (StringFind(OrderComment(), "partial close") < 0)
continue;
returnOrderTicket();
}
}
return0;
}
int GetTicketByPartialClose(string comment, int fromStart, int orderType, datetime openTime)
{
string sTicket = StringSubstr(comment, fromStart + 6);
int iTicket = (int)StringToInteger(sTicket);
int type = OrderType();
if (!OrderSelect(iTicket, SELECT_BY_TICKET))
return0;
if (OrderType() == type) // Дочерний ордер указывает на родителя - уходимreturn iTicket;
// Дочерний ордер указывает на противоположный ордер. Необходимо искать родительскийfor (int i = OrdersHistoryTotal() - 1; i >= 0; i--)
{
if (!OrderSelect(i, SELECT_BY_POS, MODE_HISTORY))
continue;
if (OrderType() != orderType || OrderOpenTime() != openTime)
continue;
int iFind = StringFind(OrderComment(), "close hedge by #");
if (iFind < 0)
continue;
sTicket = StringSubstr(OrderComment(), iFind + 16);
int iNewTicket = (int)StringToInteger(sTicket);
if (iNewTicket != iTicket)
continue;
returnOrderTicket();
}
return0;
}
Fácil de usar:
for (int i = OrdersTotal() - 1; i >= 0; i--)
{
if (!OrderSelect(i, SELECT_BY_POS))
continue;
....
int nFromTicket = GetSignOfPartialOrCloseByClose(); // Обязательно последней строкой в теле цикла, т. к. может измениться текущий выбранный ордер
}
Além disso, em seu código, o Stop Loss é verificado imediatamente após a abertura do pedido. Parece que depois de abrir uma ordem pendente, este código não é mais executado. Ou seja, é preciso separar os ramos de execução. Um é responsável pela definição do pedido, e o segundo é responsável pelo seu acompanhamento.
Obrigado por sua resposta detalhada!
Seguindo seu conselho, eu separei as filiais e tudo funciona.
Depois me deparei com o problema da abertura simultânea de 10-15 ordens pendentes, resolvi este problema adicionando-o depois de seu código:
if (OrdersTotal ()>0) return;
Tenho certeza de que há uma maneira melhor.
Por seu código, você poderia explicar o que 1; i >=0; --i significa?
Por favor, ajude-me a entender como escrever um indicador. Eu desenhei um tal boneco, como fazer um comprimento de indicador a ser desenhado em pontos de tamanho acima da atual Proposta, a partir do momento em que o indicador é colocado no gráfico? Talvez o erro seja que eu esteja mudando esta matriz na direção errada?
Eu sei que é "canônico", sem qualquer pré-cálculo etc., mas eu preciso disso assim
#property copyright"Copyright 2018, MetaQuotes Software Corp."#property link"https://www.mql5.com"#property version"1.00"#property indicator_chart_window#property indicator_buffers1#property indicator_plots1//---- plot #property indicator_label1"myInd"#property indicator_type1DRAW_LINE#property indicator_color1 Blue
#property indicator_style1STYLE_SOLID#property indicator_width11double buff[], Bid;
inputint lenght = 50, size = 5;
//+------------------------------------------------------------------+//| Custom indicator initialization function |//+------------------------------------------------------------------+intOnInit()
{
//--- indicator buffers mappingArrayResize(buff, 50);
ArrayInitialize(buff, 0);
SetIndexBuffer(0, buff, INDICATOR_DATA);
//--- установим метку для отображения в DataWindowPlotIndexSetString(0,PLOT_LABEL,"myInd");
//--- установим имя для показа в отдельном подокне и во всплывающей подсказкеIndicatorSetString(INDICATOR_SHORTNAME,"myInd");
//--- укажем точность отображения значений индикатораIndicatorSetInteger(INDICATOR_DIGITS, _Point);
//---return(INIT_SUCCEEDED);
}
//+------------------------------------------------------------------+//| Custom indicator iteration function |//+------------------------------------------------------------------+intOnCalculate(constint rates_total,
constint prev_calculated,
constdatetime &time[],
constdouble &open[],
constdouble &high[],
constdouble &low[],
constdouble &close[],
constlong &tick_volume[],
constlong &volume[],
constint &spread[])
{
//---Bid = SymbolInfoDouble(_Symbol, SYMBOL_BID);
for(int i = lenght-1; i>0; i--){
buff[i] = buff[i-1];
}
buff[0] = Bid+size;
//--- return value of prev_calculated for next callreturn(rates_total);
}
//+------------------------------------------------------------------+
Por favor, ajude-me a entender como escrever um indicador. Eu desenhei um tal boneco, como fazer um comprimento de indicador a ser desenhado em pontos de tamanho acima da atual Proposta, a partir do momento em que o indicador é colocado no gráfico? Talvez o erro seja que eu esteja mudando esta matriz na direção errada?
Eu sei que é "canônico", sem pré-cálculo e coisas assim.
O que é o cânone? Há um documento oficial - é exatamente como o seu.
1. você deve definir a serialização de todas as matrizes usadas dentro da OnCalculate.
Antes de entrar no loop, coloque buff[length]=Bid+size; - você terá aproximadamente o que você quer. Uma linha curva e no final uma "viseira" no tamanho Bid+size
3. observar os limites da matriz. É claro que as tarifas_total é dificilmente <comprimento, mas você não pode errar :-)
4.
buff[i] = buff[i+1]; // если тайм-серия (а вы подразумеваете их) то +
Que reviravolta!))))
Ordem 1 (de# não, até#2) -- > Ordem2 (de#1, até#3) -- > Ordem3 (de#2, até# não)
A partir disto, você pode encontrar toda a cadeia.
Olhamos para o comentário aberto e, se houver de #XXX, significa que ele foi fechado parcialmente - procure pelo bilhete XXX do comentário e procure-o na história. Olhe lá comentário - se houver de#YYYY - significa que também foi parcialmente fechado antes - olhe bilhete YYY de comentário e procure-o na história. Veja o comentário - se houver de#ZZZZ - significa que também foi parcialmente fechado antes - repita a busca. Se não há nenhum de#..., então é o primeiro de toda a cadeia.
Order 1 (de# não, até#2) -- > Order2 (de#1, até#3) -- > Order3 (de#2, até# não)
A partir disto, você pode encontrar toda a cadeia.
Olhamos para o comentário aberto e, se houver de #XXX, significa que anteriormente estava parcialmente fechado - procure pelo bilhete XXX do comentário e procure-o na história. Olhe lá comentário - se houver de#YYYY - significa que também foi parcialmente fechado antes - olhe bilhete YYY de comentário e procure-o na história. Veja o comentário - se houver de#ZZZZ - significa que também foi parcialmente fechado antes - repita a busca. Se não há nenhum de#..., então é o primeiro de toda a cadeia.
Obrigado, pode haver uma ordem na direção oposta, que eu também cortarei. Tenho medo de ficar confuso. Eu acho que seria mais fácil usar a ordem de lucro de uma determinada data, é claro, se formos capazes de descobrir quando a posição foi aberta, porque a data muda quando a posição é parcialmente fechada
Order 1 (de# não, até#2) -- > Order2 (de#1, até#3) -- > Order3 (de#2, até# não)
A partir disto, você pode encontrar toda a cadeia.
Veja comentário aberto e se houver de #XXX, significa que foi parcialmente fechado antes - procure o bilhete XXX a partir de comentário e procure-o na história. Veja o comentário lá - se houver de#YYYY - então também foi parcialmente fechado antes - veja o bilhete YYY a partir do comentário e procure por ele na história. Veja o comentário - se houver de#ZZZZ - significa que também foi parcialmente fechado antes - repita a busca. Se não há nenhum de#..., então é o primeiro de toda a cadeia.
Artem você sabe que este nem sempre é o caso. E para não traçar uma corrente para não interrogar o terminal três vezes - a história é conduzida, mesmo assim, em matrizes e estruturas próprias. Não é diferente de manter seu próprio banco de dados, exceto pelas etapas extras
O terminal e seu API é o nível mais baixo possível. E para implementar a lógica do robô, é lógico fazer a contabilidade em seus termos (comércio, cadeia, grupo, transação - todos a chamam de forma diferente). É apenas sensato mantê-lo separado e não tentar reconstruí-lo a cada espirro (tick/bar).
Você sabe que este nem sempre é o caso, Artyom. E assim, não é preciso perguntar três vezes ao terminal ao rastrear a cadeia - a história ainda é conduzida para suas próprias matrizes e estruturas. Não é diferente de manter seu próprio banco de dados, exceto pelas etapas extras
O terminal e seu API é o nível mais baixo possível. E para a realização da lógica robótica, é lógico manter a contabilidade em seus termos (comércio, cadeia, grupo, transação - todos a chamam de forma diferente). É apenas sensato mantê-lo separado e não tentar reconstruí-lo a cada espirro (tick/bar).
Há muito tempo eu tenho tudo feito - não leio a história todas as vezes - mas está sempre atualizado, e posso encontrar tudo o que preciso lá com facilidade e muito rapidamente. Mas para aconselhar alguém a fazer o mesmo, eu preciso de pelo menos alguns artigos. E assim escrevi a lógica de encontrar a cadeia inteira.
Obrigado, pode haver uma ordem na direção oposta que eu também triturarei. Tenho medo de ficar confuso. Eu acho que seria mais fácil usar a função Lucro para fechar uma posição a partir de uma determinada data, é claro, se você puder descobrir quando a posição foi aberta, porque em um fechamento parcial a data muda
Para buscar uma cadeia, basta conhecer o ticket da ordem, a cadeia inteira da qual você quer saber - passe o ticket como parâmetro para a função de busca, e a saída - uma matriz preenchida ou uma matriz de estruturas com todos os dados de cada ordem da cadeia inteira.
Uma matriz preenchida ou uma matriz de estruturas com todos os dados de cada ordem de toda a cadeia.
Eu nem sei aproximadamente o que você acabou de dizer.
Ao menos me mostre um exemplo de como deveria ser.
Eu nem sei aproximadamente o que você acabou de dizer.
Pelo menos me dê um exemplo de como deveria ser.
Eu resolvo o problema da seguinte maneira: busca de correntes pela história. Bem, para que a história esteja inequivocamente disponível, eu utilizo duas variantes:
Funções para determinar a ordem pai, se a ordem atual não for a principal:
Fácil de usar:
O erro mais grosseiro aqui é especificar o valor 100 em vez do bilhete no argumento OrderDelete().
O próximo erro não é tão rude, mas está relacionado ao fato de que o valor calculado de Stop Loss é verificado, não seu valor real.
O tipo de pedido também não é verificado. E se tivermos escolhido uma ordem de mercado? Como apagá-lo? O símbolo do pedido não foi verificado.
Levando em consideração estes erros, obtemos o código de eliminação da ordem pendente quando o preço atinge seu Stop Loss:
Além disso, em seu código, o Stop Loss é verificado imediatamente após a abertura do pedido. Parece que depois de abrir uma ordem pendente, este código não é mais executado. Ou seja, é preciso separar os ramos de execução. Um é responsável pela definição do pedido, e o segundo é responsável pelo seu acompanhamento.Obrigado por sua resposta detalhada!
Seguindo seu conselho, eu separei as filiais e tudo funciona.
Depois me deparei com o problema da abertura simultânea de 10-15 ordens pendentes, resolvi este problema adicionando-o depois de seu código:
Tenho certeza de que há uma maneira melhor.
Por seu código, você poderia explicar o que 1; i >=0; --i significa?
Por favor, ajude-me a entender como escrever um indicador. Eu desenhei um tal boneco, como fazer um comprimento de indicador a ser desenhado em pontos de tamanho acima da atual Proposta, a partir do momento em que o indicador é colocado no gráfico? Talvez o erro seja que eu esteja mudando esta matriz na direção errada?
Eu sei que é "canônico", sem qualquer pré-cálculo etc., mas eu preciso disso assim
Por favor, ajude-me a entender como escrever um indicador. Eu desenhei um tal boneco, como fazer um comprimento de indicador a ser desenhado em pontos de tamanho acima da atual Proposta, a partir do momento em que o indicador é colocado no gráfico? Talvez o erro seja que eu esteja mudando esta matriz na direção errada?
Eu sei que é "canônico", sem pré-cálculo e coisas assim.
O que é o cânone? Há um documento oficial - é exatamente como o seu.
1. você deve definir a serialização de todas as matrizes usadas dentro da OnCalculate.
Antes de entrar no loop, coloque buff[length]=Bid+size; - você terá aproximadamente o que você quer. Uma linha curva e no final uma "viseira" no tamanho Bid+size
3. observar os limites da matriz. É claro que as tarifas_total é dificilmente <comprimento, mas você não pode errar :-)
4.buff[i] = buff[i+1]; // если тайм-серия (а вы подразумеваете их) то +