se aberto no primeiro bar, estamos olhando de zero a zero?
Isto é um pouco reconfortante caso o preço de abertura do pedido já seja muito mais alto do que Baixo no momento da abertura. Ou seja, não usamos a barra de abertura para buscas. É para isso que serve o PERÍODO_M1.
Sepulca: Esta é uma pequena cobertura no caso do preço de abertura do pedido já ser significativamente mais alto do que Baixo no momento da abertura. Isto é, não usamos a barra de abertura para a busca. É para isso que serve o PERÍODO_M1.
Eu o faria de uma maneira diferente. Em geral, eu começaria a procurar somente quando a posição tivesse durado mais de uma barra. Afinal de contas, o melhor preço pode estar logo na barra de abertura, e nós o desperdiçaremos.
artmedia70: Eu o faria de forma diferente. Em geral, eu só começaria a procurar quando a posição tivesse durado mais de uma barra. Afinal, o melhor preço pode estar apenas no bar de abertura e nós o desperdiçamos...
Eu concordo. Seria provavelmente mais eficiente lembrar o preço mínimo (ou máximo) para cada ordem aberta na matriz em cada cartela, e fechar as ordens quando a condição é atingida, do que procurar novamente o mínimo desde o momento em que a ordem foi aberta, por assim dizer:
ShortOrderTicket[i]=OrderSend(Symbol(),OP_SELL,......
if(ShortOrderTicket[i]>=0) min[i]=Bid;
//.....................................................//На каждом тике обновляем минимумы для каждого открытого ордераfor(i=0;i<N;i++){
if(ShortOrderTicket[i]>=0){
min[i]=MathMin(min[i],Ask);
}
// Если достигнуто условие, закрываем ордерif(Ask>min[i]+Delta) if(OrderClose(ShortOrderTicket[i],.....))ShortOrderTicket[i]=-1;
}
E em caso de problemas como perda de conexão, reinício do conselheiro, etc. Eu modificaria de tempos em tempos o tempo de paralisação de pedidos.
artmedia70: Eu argumentei que a matriz deve ser passada aqui por referência. Caso contrário, a função terá que funcionar com apenas uma matriz estritamente definida. Mesmo que você tenha definido globalmente.
Hmm. Depende de qual matriz é passada para a função de chamada. Se for uma matriz específica, então a função chamada funcionará com ela. Porque isso é...
Se, por exemplo,
void FindOrders(int massive[])
{
int oType;
ArrayInitialize(massive, 0);
for (int i=OrdersTotal() - 1; i>=0; i--)
{
if (!OrderSelect(i,SELECT_BY_POS,MODE_TRADES)) continue;
if (OrderSymbol() != Symbol()) continue;
if (OrderMagicNumber() != i_magic) continue;
oType = OrderType();
massive[oType] = massive[oType] + 1;
}
}
Forexman77: Você pode me dizer como descobrir o tamanho do spread, no momento da abertura de um comércio, ou, melhor, como exibi-lo no log?
Se (spread) == algum valor, então... faça algo... (Por exemplo, abrir um pedido ou imprimir seu valor na revista). Ou vice-versa, se não for igual ou maior que (menos que) algum valor, então o exibimos na revista e fazemos algo. Você pode fazer o que quiser.
Vou repetir a pergunta que fiz ontem. Não quero colocá-lo em uma linha separada. Se algo não estiver claro, responderei a todas as perguntas.
Ainda estou tendo dificuldades para fechar as posições necessárias. A situação é a seguinte:
1. o fechamento das posições está sendo rastreado.
2. Assim que a última posição tiver fechado na linha de chegada. ...todas as posições abertas e pendentes devem ser fechadas de uma só vez. Tudo é fechado por lotes, ou seja, grandes lotes ao mesmo tempo, e depois menores. Isto se destina apenas a ganhar experiência com pedidos.
A implementação é a seguinte:
No início() em cada tic-tac:
for (int ord=OrdersTotal()-1; ord>=0; ord--)
{
if (!OrderSelect(ord,SELECT_BY_POS)) continue;
if (OrderMagicNumber() != i_magic) continue;
if (OrderSymbol() != Symbol()) continue;
if (OrderType() == 6) continue;
g_ticket = OrderTicket();
g_type = OrderType();
// Блок модификации ордеров
if (i_sl != 0 || i_tp != 0)
{
if (OrderStopLoss() == 0 && OrderTakeProfit() == 0)
{
OrdersModifyer(g_ticket);
}
}
// Закрытие всех ордеров, если последний ордер закрыт
if (isCloseByTakeLastOpenPos(2))
{
// if (g_type < 2)
{
ClosePosBySortLots();
}
//else
if (g_type > 1)
{
DeletePendingOrders(g_ticket);
}
}
}
Estamos interessados em fechar ordens de mercado, uma vez que o pendente é eliminado conforme necessário. Aqui está o que temos:
//+-------------------------------------------------------------------------------------+//| Получаем состояние последней позиции (Открыта или закрыта) |//+-------------------------------------------------------------------------------------+bool isCloseByTakeLastOpenPos(int delta)
{
datetime lastOrderCloseTime = -1, // Время закрытия последнего открытого ордера
lastOOTHist = -1; // Время открытия последнего открытого ордера из историиint j = -1;
pr ("Запустилась функция isCloseByTakeLastOpenPos");
for (int i=OrdersHistoryTotal()-1; i>=0; i--)
{
if (!OrderSelect(i, SELECT_BY_POS, MODE_HISTORY)) continue;
if (OrderMagicNumber() != i_magic) continue;
if (OrderSymbol() != Symbol()) continue;
if (OrderType() > 1) continue; // Все удалённые отложки нас не интересуют..if (lastOrderCloseTime < OrderCloseTime()) // Находим время закрытия..
{
lastOrderCloseTime = OrderCloseTime(); // ..последней закрытой позиции в истории
j = i;
pr ("j = " + j + " " + TimeToStr(TimeCurrent()));
}
}
if (OrderSelect(j, SELECT_BY_POS, MODE_HISTORY))
{
if (OrderProfit() + OrderCommission() + OrderSwap() <= 0) return (false);
// pr ("OTP() = " + OrderTakeProfit() + "; OCP() " + OrderClosePrice() + " " + TimeToStr(TimeCurrent()));// pr ("OOP() = " + OrderOpenPrice() + "; OCP() " + OrderClosePrice() + " " + TimeToStr(TimeCurrent()));if (MathAbs(OrderTakeProfit() - OrderClosePrice()) > delta * pt) return (false);
else
{
lastOOTHist = OrderOpenTime();
Comment("\n", "FUNC isCloseByTakeLastOpenPos: ",
"\n", "j = ", j,
"\n", "lastOOTHist = ", TimeToStr(lastOOTHist, TIME_SECONDS));
}
}
else
{
Comment("\n", "FUNC isCloseByTakeLastOpenPos: ",
"\n", "j = ", j,
"\n", "не удалось выбрать ордер в истории");
return(false);
}
for(int h=OrdersTotal()-1; h>=0; h--)
{
if (OrderSelect(h, SELECT_BY_POS, MODE_TRADES))
{
if (OrderMagicNumber() != i_magic) continue;
if (OrderSymbol() != Symbol()) continue;
if (OrderType() > 1) continue;
if (lastOOTHist < OrderOpenTime()) return(false); // Выбранная рыночная позиция открыта позже закрытой по тейку
}
else {Print("FUNC isCloseByTakeLastOpenPos : не удалось выбрать рыночный ордер");return(false);}
}
return (true);
}
//+-------------------------------------------------------------------------------------+//| Закрытие ордеров, отсортированных по размеру лотов |//+-------------------------------------------------------------------------------------+void ClosePosBySortLots()
{
double a[][2];
int p = 0;
for (int i=OrdersTotal()-1; i>=0; i--)
{
if (!OrderSelect(i, SELECT_BY_POS, MODE_TRADES)) continue;
if (OrderMagicNumber() != i_magic) continue;
if (OrderSymbol() != Symbol()) continue;
if (OrderType() < 2)
{
p++;
ArrayResize(a, p);
a[p-1][0] = OrderLots();
a[p-1][1] = OrderTicket();
}
}
pr ("ClosePosBySortLots(): " + "p = " + p);
if (p > 0)
{
ArraySort(a, WHOLE_ARRAY, 0, MODE_DESCEND);
for(i=0; i<p; i++)
{
if (OrderSelect(a[i][1], SELECT_BY_TICKET, MODE_TRADES))
{
if (OrderCloseTime() == 0) ClosePosBySelect();
}
}
}
}
//+-------------------------------------------------------------------------------------+//| Закрытие одного, предварительно выбранного ордера |//+-------------------------------------------------------------------------------------+void ClosePosBySelect()
{
bool fc;
color clClose, clCloseBuy = Blue, clCloseSell = Red;
double ll, pa, pb, pp;
int err, it, NumberOfTry = 3;
if (OrderType() == OP_BUY || OrderType() == OP_SELL)
{
for (it=1; it<=NumberOfTry; it++)
{
while (!IsTradeAllowed()) Sleep(5000);
RefreshRates();
pa = MarketInfo(OrderSymbol(), MODE_ASK);
pb = MarketInfo(OrderSymbol(), MODE_BID);
if (OrderType() == OP_BUY)
{
pp = pb; clClose = clCloseBuy;
}
else
{
pp = pa; clClose = clCloseSell;
}
ll = OrderLots();
fc = OrderClose(OrderTicket(), ll, pp, 30, clClose);
if (fc)
{
break;
}
else
{
err = GetLastError();
}
}
}
elsePrint("Некорректная торговая операция. Close ");
}
Por alguma razão, algumas das ordens não estão sendo fechadas. Eu imprimo alguns segmentos quando os vejo, não entendo nada. Aqui está um exemplo:
O comentário mostra que lastOOTHist = 01:30: 00, embora isto não seja realmente correto. Se verificarmos a lastOOTHist na janela de resultados, veremos que
Hmm. Depende de qual matriz é passada para a função de chamada. Se for uma matriz específica, então a função chamada funcionará com ela. Porque isso é...
Se, por exemplo,
Chamando-a desta forma:
Funciona com a matriz OrdersMassive
E assim:
Com a matriz MassiveOfOrders.
Quando você passa uma variável (array) para uma função por valor, uma variável local é criada dentro da função e você a declara no cabeçalho: myFunct(int my_var). Desta forma, as mudanças desta variável não podem ser vistas fora da função. E no caso de um array, o compilador irá lembrá-lo disso.
Se você quiser que as mudanças no valor da variável sejam visíveis fora (fora da função), passe as variáveis por referência : myFunct(int & my_var)
Depende de qual matriz é passada para a função de chamada. Se houver uma determinada matriz, então a função chamada funcionará com ela. É assim...
Se, por exemplo,
Chamando-a assim:
Funciona com a matriz OrdersMassive
E desta forma:
Com array massiveOfOrders
Exatamente. É isso que estou dizendo - por que você quer que uma matriz específica seja codificada na própria função, se você pode passar qualquer matriz do mesmo tamanho e digitar dentro dela.
Eu o teria feito desta maneira:
P.S. Respondeu ao mesmo tempo))))
Eu não entendo:
se aberto no primeiro bar, olhando de zero a zero?
Eu não entendo:
se aberto no primeiro bar, estamos olhando de zero a zero?
Esta é uma pequena cobertura no caso do preço de abertura do pedido já ser significativamente mais alto do que Baixo no momento da abertura. Isto é, não usamos a barra de abertura para a busca. É para isso que serve o PERÍODO_M1.
Eu o faria de forma diferente. Em geral, eu só começaria a procurar quando a posição tivesse durado mais de uma barra. Afinal, o melhor preço pode estar apenas no bar de abertura e nós o desperdiçamos...
Eu concordo. Seria provavelmente mais eficiente lembrar o preço mínimo (ou máximo) para cada ordem aberta na matriz em cada cartela, e fechar as ordens quando a condição é atingida, do que procurar novamente o mínimo desde o momento em que a ordem foi aberta, por assim dizer:
E em caso de problemas como perda de conexão, reinício do conselheiro, etc. Eu modificaria de tempos em tempos o tempo de paralisação de pedidos.Eu argumentei que a matriz deve ser passada aqui por referência. Caso contrário, a função terá que funcionar com apenas uma matriz estritamente definida. Mesmo que você tenha definido globalmente.
Hmm. Depende de qual matriz é passada para a função de chamada. Se for uma matriz específica, então a função chamada funcionará com ela. Porque isso é...
Se, por exemplo,
Chamando-a desta forma:
Funciona com a matriz OrdersMassive.
E assim:
Com a matriz MassiveOfOrders.
Você pode me dizer como descobrir o tamanho do spread, no momento da abertura de um comércio, ou, melhor, como exibi-lo no log?
Se (spread) == algum valor, então... faça algo... (Por exemplo, abrir um pedido ou imprimir seu valor na revista). Ou vice-versa, se não for igual ou maior que (menos que) algum valor, então o exibimos na revista e fazemos algo. Você pode fazer o que quiser.
Vou repetir a pergunta que fiz ontem. Não quero colocá-lo em uma linha separada. Se algo não estiver claro, responderei a todas as perguntas.
Ainda estou tendo dificuldades para fechar as posições necessárias. A situação é a seguinte:
1. o fechamento das posições está sendo rastreado.
2. Assim que a última posição tiver fechado na linha de chegada. ...todas as posições abertas e pendentes devem ser fechadas de uma só vez. Tudo é fechado por lotes, ou seja, grandes lotes ao mesmo tempo, e depois menores. Isto se destina apenas a ganhar experiência com pedidos.
A implementação é a seguinte:
No início() em cada tic-tac:
for (int ord=OrdersTotal()-1; ord>=0; ord--) { if (!OrderSelect(ord,SELECT_BY_POS)) continue; if (OrderMagicNumber() != i_magic) continue; if (OrderSymbol() != Symbol()) continue; if (OrderType() == 6) continue; g_ticket = OrderTicket(); g_type = OrderType(); // Блок модификации ордеров if (i_sl != 0 || i_tp != 0) { if (OrderStopLoss() == 0 && OrderTakeProfit() == 0) { OrdersModifyer(g_ticket); } } // Закрытие всех ордеров, если последний ордер закрыт if (isCloseByTakeLastOpenPos(2)) { // if (g_type < 2) { ClosePosBySortLots(); } //else if (g_type > 1) { DeletePendingOrders(g_ticket); } } }Estamos interessados em fechar ordens de mercado, uma vez que o pendente é eliminado conforme necessário. Aqui está o que temos:
Por alguma razão, algumas das ordens não estão sendo fechadas. Eu imprimo alguns segmentos quando os vejo, não entendo nada. Aqui está um exemplo:
O comentário mostra que lastOOTHist = 01:30: 00, embora isto não seja realmente correto. Se verificarmos a lastOOTHist na janela de resultados, veremos que
seus horários de fechamento são diferentes...
O que está errado aqui?
Hmm. Depende de qual matriz é passada para a função de chamada. Se for uma matriz específica, então a função chamada funcionará com ela. Porque isso é...
Se, por exemplo,
Chamando-a desta forma:
Funciona com a matriz OrdersMassive
E assim:
Com a matriz MassiveOfOrders.
Quando você passa uma variável (array) para uma função por valor, uma variável local é criada dentro da função e você a declara no cabeçalho: myFunct(int my_var). Desta forma, as mudanças desta variável não podem ser vistas fora da função. E no caso de um array, o compilador irá lembrá-lo disso.
Se você quiser que as mudanças no valor da variável sejam visíveis fora (fora da função), passe as variáveis por referência : myFunct(int & my_var)
Depende de qual matriz é passada para a função de chamada. Se houver uma determinada matriz, então a função chamada funcionará com ela. É assim...
Se, por exemplo,
Chamando-a assim:
Funciona com a matriz OrdersMassive
E desta forma:
Com array massiveOfOrders