New MetaTrader 5 Platform Build 5260: Enhancements in Algo Forge, extended OpenBLAS support, and new inheritance rules in MQL5 - page 9

 
amrali #:

Execuse me Alain, 0.30000000000000004 is the actual return value from RYU library. It is  consistent with the Expert log output.

No idea what is this library you are using. Here is the one from the RYU algorithm creator https://github.com/ulfjack/ryu, see also this paper https://www.researchgate.net/publication/329410883_Ryu_fast_float-to-string_conversion

I don't see what the Expert log has to do here. 0.3 is the correct RYU value, that's it.

You can test yourself:

I don't have the souce code. Ilyas can confirm the issue.

Here, the shortest string may have 1,2,.. up to 17 significant digits. RYU only picks the shortest string that round-trips (when converted back to a floating-point ...)

That's wrong, I posted the correct RYU definition previously : "the shortest, correct decimal representation that..." round-trips.

C++ code.

#include <iostream>
#include <format>
#include <charconv>
#include <string>

std::string doubleToString(double number)
{
    char buffer[24];
    std::to_chars_result err = std::to_chars(buffer, buffer+sizeof(buffer), number);
    return std::string(buffer, err.ptr);
}
int main() {
    double x = 0.3;
    // C++20 std::format uses the shortest decimal representation by default
    std::cout << std::format("C++20 {}", x) << std::endl;     // Output: 0.3
    // C++17 from https://stackoverflow.com/questions/65810673/format-a-double-without-losing-precision-but-with-a-minimum-number-of-digits
    std::cout << "C++17 " << doubleToString(x) << std::endl;  // Output: 0.3
    return 0;
}

The MQL 5 Print() uses the RYU algorithm since build 3210.

No it's not, it's round-trips (fixed at you request).

I think you are mixing RYU algorithm and Round-trips ?

GitHub - ulfjack/ryu: Converts floating point numbers to decimal strings
GitHub - ulfjack/ryu: Converts floating point numbers to decimal strings
  • ulfjack
  • github.com
This project contains routines to convert IEEE-754 floating-point numbers to decimal strings using shortest, fixed , and scientific formatting. The primary implementation is in C, and there is a port of the shortest conversion to Java. All algorithms have been published in peer-reviewed publications. At the time of this writing, these are the...
 
Alain Verleyen #:


Forum on trading, automated trading systems and testing trading strategies

C++ code.

#include <iostream>
#include <format>
#include <charconv>
#include <string>

int main() {
    double x = 0.3;
}
std::to_chars float-to-string uses Ryu (MSVC/STL, Clang/libc++) or Dragonbox (GCC/libstdc++).

I corrected your code to x = 0.1 + 0.2, the same as I posted before:

#include <iostream>
#include <format>
#include <charconv>
#include <string>

std::string doubleToString(double number) {
    char buffer[24];
    std::to_chars_result err = std::to_chars(buffer, buffer+sizeof(buffer), number);
    return std::string(buffer, err.ptr);
}
int main() {
    double x = 0.1 + 0.2;
    std::cout << "C++17 RYU: " << doubleToString(x) << std::endl;
    return 0;
}

output:

C++17 RYU: 0.30000000000000004


 
amrali #:
std::to_chars float-to-string uses Ryu (MSVC/STL, Clang/libc++) or Dragonbox (GCC/libstdc++).

I corrected your code to x = 0.1 + 0.2, the same as I posted before:

output:

C++17 RYU: 0.30000000000000004


Got it, I had missed that point and was focused on x = 0.3. 
 
Alain Verleyen #:
Got it, I add missed that point and was focused on x = 0.3
At least i am not the only who was initially confused. Didnt find the time to verify.

Thank you amrali for the clarification in this matter. (Again)
 
Ilyas #:

Thank you for your message.

In the tooltip all integers type were interpreted as ulong.
I changed this behaviour, all integer type values will cast to the nearest unsigned type (special 1 bit integer type for bool) before output to the tooltip

Also for a double type values "%.16g" will be used instead of "%.15g" for the tooltip
The watchlist uses RYU for a double type values (IMHO it is fastest and precize algorithm)


Ilyas, would it be possible to make the watchlist include the ability to edit the values additionally to showing them?

Such that a displayed value could actually be changed manually, by hand?
 
Alain Verleyen #:
Got it, I had missed that point and was focused on x = 0.3

by the way, the link you posted on SO https://stackoverflow.com/questions/65810673/format-a-double-without-losing-precision-but-with-a-minimum-number-of-digits typically describes the situation that a developper faces when converting double -> string.

Also this lecture from microsoft https://www.youtube.com/watch?v=4P_kbF0EbZM explains the concept of "shortest round-trip conversion".

 
amrali #:

by the way, the link you posted on SO https://stackoverflow.com/questions/65810673/format-a-double-without-losing-precision-but-with-a-minimum-number-of-digits typically describes the situation that a developper faces when converting double -> string.

Also this lecture from microsoft https://www.youtube.com/watch?v=4P_kbF0EbZM explains the concept of "shortest round-trip conversion".

Actually when I convert 0.3 or 0.1+0.2 to a string, I was expecting (and still expect) to see 0.3 in both case. I don't care about all these decimals (as a string in a log or in the Watchlist), that's also what confused me about RYU. If I need to see the decimals I can use a format to get them.

Anyway...

 
Alain Verleyen #:

Actually when I convert 0.3 or 0.1+0.2 to a string, I was expecting (and still expect) to see 0.3 in both case. I don't care about all these decimals (as a string in a log or in the Watchlist), that's also what confused me about RYU. If I need to see the decimals I can use a format to get them.

Anyway...

Different people have different needs, but from the noticeable drop in forum posts complaining about vague floating-point inaccuracies, I’m confident that switching Print(), Alert() and string() to use RYU for doubles since build 3120 was the right move.
 
amrali #:
Different people have different needs, but from the noticeable drop in forum posts complaining about vague floating-point inaccuracies, I’m confident that switching Print(), Alert() and string() to use RYU for doubles since build 3120 was the right move.
For what real needs do you need to see 0.30000000000000004 in MT5 ?
 
1. Consistency across the terminal: seeing two different strings for the same number in the debugger (watchlist and a wrong tooltip) and a third different one in the expert log is not a nice thing.
2. Determine why logical comparisons can fail for apparently equal amounts (e.g., comparing the price to some price level or a value that was reached to via two different calculation pathways)
3. Knowing when rounding of prices or lots are necessary (for chopping round-off errors at the far right).

Alain, I think we're off-topic, there’s no point in continuing this discussion.