(C++) ToDouble
March 3, 2018 · View on GitHub
(C++) ToDouble
ToDouble is a conversion code snippet to convert a std::string to double.
ToDouble can be implemented in multiple equivalent ways (incomplete list):
- ToDouble using std::atof
- ToDouble using std::strtod
- ToDouble using std::istringstream
To conversion a std::string to any data type one can use LexicalCast and boost::lexical_cast.
ToDouble using std::atof
#include <cstdlib> #include <string> //From http://www.richelbilderbeek.nl/CppToDouble.htm double ToDouble(const std::string& s) { return std::atof(s.c_str()); }
ToDouble using std::istringstream
The implementation below is similar to the C++ FAQ Lite's convertToDouble code snippet.
#include <sstream> #include <stdexcept> #include <string> //From http://www.richelbilderbeek.nl/CppToDouble.htm double ToDouble(std::string const& s) { std::istringstream i(s); double x; if (!(i >> x)) { throw std::logic_error("std::string cannot be converted to double"); } return x; }
ToDouble using std::strtod
#include <cstdlib> #include <string> //From http://www.richelbilderbeek.nl/CppToDouble.htm double ToDouble(const std::string& s) { return std::strtod(s.c_str(),0); }
ToDouble tests
In the code below, all ToDouble flavors are compared and found out equivalent.
#include <algorithm> #include <cassert> #include <cstdlib> #include <iostream> #include <sstream> #include <stdexcept> #include <string> //From http://www.richelbilderbeek.nl/CppToDouble.htm double ToDoubleUsingAtof(const std::string& s) { return std::atof(s.c_str()); } //From http://www.richelbilderbeek.nl/CppToDouble.htm double ToDoubleUsingStrtod(const std::string& s) { return std::strtod(s.c_str(),0); } //From http://www.richelbilderbeek.nl/CppToDouble.htm double ToDoubleUsingStream(std::string const& s) { std::istringstream i(s); double x; if (!(i >> x)) { throw std::logic_error("std::string cannot be converted to double"); } return x; } const char GetRandomDigit() { switch (std::rand() % 10) { case 0: return '0'; case 1: return '1'; case 2: return '2'; case 3: return '3'; case 4: return '4'; case 5: return '5'; case 6: return '6'; case 7: return '7'; case 8: return '8'; case 9: return '9'; } } const std::string GetRandomDouble() { const std::string sign = ((std::rand() >> 4) % 2 ? "+" : "-"); std::string s1; s1.resize(1 + (std::rand() % 3)); std::generate(s1.begin(),s1.end(),GetRandomDigit); std::string s2; s2.resize(1 + (std::rand() % 5)); std::generate(s2.begin(),s2.end(),GetRandomDigit); const std::string s = sign + s1 + "." + s2; return s; } int main() { for (int i=0; i!=20; ++i) { const std::string s = GetRandomDouble(); std::cout << s << ":\t" << ToDoubleUsingAtof(s) << '\n'; assert(ToDoubleUsingAtof(s)==ToDoubleUsingStrtod(s)); assert(ToDoubleUsingAtof(s)==ToDoubleUsingStream(s)); } }
Screen output:
+67.3: 67.3 +29.27: 29.27 +36.6: 36.6 -18.920: -18.92 +75.22897: 75.229 +12.31947: 12.3195 +503.10: 503.1 -2.6: -2.6 -5.76569: -5.76569 +452.4: 452.4 -430.868: -430.868 +3.49: 3.49 +6.9266: 6.9266 -504.7172: -504.717 +2.10: 2.1 +59.90917: 59.9092 -159.767: -159.767 +5.39: 5.39 +12.39088: 12.3909 +96.8561: 96.8561