Programming in MQL5 for traders - source codes from the book. Part 7 :
Author: MetaQuotes

- www.mql5.com
Can you tell me if this is an error or I don't understand something?
MarginProfitMeter.mqh file.
// Convert amount of 'current' money into 'account' money bool Convert(const string current, const string account, const bool ask, double &margin, const datetime moment = 0) { string rate; int dir = FindExchangeRate(current, account, rate); if(dir == +1) { margin *= moment == 0 ? SymbolInfoDouble(rate, ask ? SYMBOL_BID : SYMBOL_ASK) : GetHistoricPrice(rate, moment, ask); } else if(dir == -1) { margin /= moment == 0 ? SymbolInfoDouble(rate, ask ? SYMBOL_ASK : SYMBOL_BID) : GetHistoricPrice(rate, moment, ask); } else { static bool once = false; if(!once) { Print("Can't convert ", current, " -> ", account); once = true; } } return true; }
It is impossible to divide by zero, isn't it?
Also, this method should return the margin, but it returns the price. I understand that somewhere this price should be multiplied by the contract size, but I don't understand where to do it correctly.
Should I add it in this function or where we call this function from?
Can you tell me if this is a mistake or if I'm missing something?
File MarginProfitMeter.mqh
It is impossible to divide by zero, isn't it?
Indeed, you can't.
margin /= moment == 0 ? SymbolInfoDouble(rate, ask ? SYMBOL_ASK : SYMBOL_BID) : GetHistoricPrice(rate, moment, ask);
There is a ternary operator after the division symbol with assignment "/=". So if momet==0, then:
margin /= SymbolInfoDouble(rate, ask ? SYMBOL_ASK : SYMBOL_BID)
otherwise:
margin /= GetHistoricPrice(rate, moment, ask)
But I would still add a check for zero from both functions....
Judging by the description
// Convert amount of 'current' money into 'account' money
the method converts current money (currency) into money (currency) of the deposit. And judging by the code, the method converts margin into the deposit currency.
If successful, the method will return true. And it will also calculate the new, corrected, amount of margin, storing it in the margin variable. It is a parameter in the link:
double &margin
So you can get it as a result of the calculation.
You really can't.
There is a ternary operator after the division symbol with assignment "/=". So if momet==0, then:
Yeah. That's right, a ternary operator. I'm tired this morning, I'm getting dumb.
Judging by the description
the method converts current money (currency) into deposit money (currency). And judging by the code, the method converts margin into the deposit currency.
No, that's correct now too.
I apologise, I made a little mistake in the code.
It is of little use anyway, because in the end it still counts the margin incorrectly if the volume is more than three.
EURUSD; margin = 24668.8 // OrderCalcMargin() EURUSD; margin = 10889.599999999999 // MarginProfitMeter.mqh
Margin calculation for ten contracts.
A little bit wrong. The condition (margin /= moment)==0 and then a ternary operator...
Somehow I don't agree. Try to fulfil this condition first:
double margin = 1.5; datetime moment = 0; margin /= moment;
Then you are dividing hedgehogs into hedgehogs, which is questionable in itself.
And assignment operations have a very low priority, only zpt has a lower priority.
The compiler gets angry too:
possible loss of data due to type conversion from 'datetime' to 'double'
And the logic of the function is margin conversion. As far as I understand, moment = 0 is now. Then:
margin /= moment == 0 ? SymbolInfoDouble(rate, ask ? SYMBOL_ASK : SYMBOL_BID) : GetHistoricPrice(rate, moment, ask);
means that if it is now, we ask for the current price. And if it's in the past, we refer to historical prices. And having got the desired price, at the very end we divide the margin value by this price with assignment.... and with your logic, it turns out that at moment = 0, we will get not margin conversion, but just the market price or the price from the past....
In general, it would be better to write in brackets for a textbook:
margin /= (moment == 0) ? SymbolInfoDouble(rate, ask ? SYMBOL_ASK : SYMBOL_BID) : GetHistoricPrice(rate, moment, ask);
Somehow I don't agree. Try to fulfil that condition first:
This then divides hedgehogs into hedgehogs, which in itself is already questionable.
And assignment operations have a very low priority, only zpt has a lower priority.
And the compiler gets angry too:
And the logic of the function is margin conversion. As far as I understand, moment = 0 is now. Then:
means that if it is now, we ask for the current price. And if it is in the past, then we refer to historical prices. And having got the desired price, at the very end we divide the margin value by this price with assignment.... and with your logic, it turns out that if moment = 0, we will not get not a margin conversion, but just a market price or a price from the past...
In general, it would be better to write in brackets for a textbook:
Convincing. I agree, I was inattentive. But if you write for a textbook and so that it would be understandable even to me, then it would be better like this
margin /= ( moment == 0 ? SymbolInfoDouble(rate, ask ? SYMBOL_ASK : SYMBOL_BID) : GetHistoricPrice(rate, moment, ask));

- Free trading apps
- Over 8,000 signals for copying
- Economic news for exploring financial markets
You agree to website policy and terms of use
MQL5 Programming for Traders – Source Codes from the Book. Part 7:
The final seventh part of the book discusses the advanced capabilities of the MQL5 API, which will be useful when developing programs for MetaTrader 5. These include custom financial symbols, built-in economic calendar events, and general-purpose technologies such as networking, databases, and cryptography.
Author: MetaQuotes