C++ 如何转换';双倍';至';字符串';以用户友好的形式

C++ 如何转换';双倍';至';字符串';以用户友好的形式,c++,string,double,C++,String,Double,我有以下问题: 客户希望以最佳方式将double类型显示为string。它需要转换为字符串并显示在表单(sms、表格和其他)上 转换代码对性能至关重要,这意味着不应使用std::stringstream+setprecision() 将params“precision”作为myToString()函数的参数来实现会很好,但是这种改进可能会严重影响我们的所有系统,我们计划在下一个版本中实现它。 但这个问题现在是实际存在的。 我编写了以下代码: inline bool toStringNew(std

我有以下问题: 客户希望以最佳方式将
double
类型显示为
string
。它需要转换为字符串并显示在表单(sms、表格和其他)上

转换代码对性能至关重要,这意味着不应使用
std::stringstream
+
setprecision()

将params“precision”作为my
ToString()
函数的参数来实现会很好,但是这种改进可能会严重影响我们的所有系统,我们计划在下一个版本中实现它。 但这个问题现在是实际存在的。
我编写了以下代码:

inline bool toStringNew(std::string& str, double const& value)
{
    static const char *zero_double_str = "0.0";
    static const double zero_double_limit = 0.001;
    static const int max_double_prec_symbol = 13;
    static const int max_fract_num = 3;
    static const int max_fract_mul = pow(10, max_fract_num);
    str.clear();
    //get digits of integer part
    double fabs_value = fabs(value);
    int64_t len = log10(fabs_value);
    //Round 2 zero
    if(len <= 0) //it means that only fraction part is present
    {
        if(fabs_value < zero_double_limit)
        {
            str = zero_double_str;
            return true;
        }
        //use default
        return boost::spirit::karma::generate(std::back_inserter(str), value);
    }
    else if(len > max_double_prec_symbol)   //default
    {
        return boost::spirit::karma::generate(std::back_inserter(str), value);
    }
    //cast to integer
    int64_t i = static_cast<int64_t>(value);
    //cast fract to integer
    int64_t fract_i = static_cast<int64_t>(round((value - i)* max_fract_mul));
    //reserve string memory
    size_t str_len = len + 1 +  max_fract_num + (value > 0 ? 0 : 1) + 1; 
    str.reserve(str_len);
    //convert integer
    boost::spirit::karma::generate(std::back_inserter(str), i);
    str+='.';
    //convert fract
    if(fract_i > 0)
    {
        str+='.';
        int64_t fract_i_len = log10(fract_i);
        //fill zero before: 0.001 -> 1 -> 001
        while(++fract_i_len < max_fract_num)
        {
            str += '0';
        }
        //remove zero after: 010 -> 01
        while(!(fract_i % 10))
        {
            fract_i = fract_i / 10;
        }
        boost::spirit::karma::generate(std::back_inserter(str), fract_i);
    }
    boost::spirit::karma::generate(std::back_inserter(str), fract_i);
    return true;
}
内联bool-toStringNew(std::string&str,double-const&value)
{
静态常量字符*zero\u double\u str=“0.0”;
静态常数双零双极限=0.001;
静态常数int max_double_prec_symbol=13;
静态常数int max_fract_num=3;
静态常数int max\u fract\u mul=pow(10,max\u fract\u num);
str.clear();
//获取整数部分的数字
双晶圆直径值=晶圆直径(值);
int64_t len=log10(晶圆厂值);
//第二零轮
if(len max\u double\u prec\u symbol)//默认值
{
返回提升::精神::业力::生成(std::返回插入器(str),值);
}
//转换为整数
int64_t i=静态强制转换(值);
//将分形转换为整数
int64_t fract_i=静态_cast(舍入((值-i)*max_fract_mul));
//保留字符串存储器
长度=长度+1+最大断裂数+(值>0?0:1)+1;
str.reserve(str_len);
//转换整数
boost::spirit::karma::generate(std::back_inserter(str),i);
str+=';
//转换分形
如果(分形i>0)
{
str+=';
int64_t fract_i_len=log10(fract_i);
//在0.001->1->001之前填充零
而(++fract_i_len01之后移除零点
而(!(分数i%10))
{
分形i=分形i/10;
}
boost::spirit::karma::generate(std::back_inserter(str),fract_i);
}
boost::spirit::karma::generate(std::back_inserter(str),fract_i);
返回true;
}
这比
double
类型的
boost::spirit::karma::generate()
快1.5倍


你能给我一些建议如何让我的客户满意吗?

如果性能至关重要,也许可以使用。它将比您自己开发的解决方案更好,而且我认为它的性能也会更好。使用
*
格式说明符,您还可以将精度设置为参数。

我将查看。我使用它进行解析和数字转换,结果表明它非常快

#include <cmath>
#include <strtk.hpp>
#include <iostream>
using namespace std;

int main ( int argc, char **argv ) 
{
   double pi = M_PI;
   std::cout << strtk::type_to_string<double>( pi ) << std::endl;
   return 0;
}
#包括
#包括
#包括
使用名称空间std;
int main(int argc,字符**argv)
{
双π=M_π;

std::你能试着测量一下
stringstream
有多慢吗?我猜,它比你预期的快。那么
std::to_string
呢?我试着使用sstream,得到了以下结果:
New-ToString()TPS=2257627.5000000000
sstream-ToString()TPS=503520.9375000000
旧ToString()TPS=1871579.8750000000
std::stringstream太slowly@DavidHaim在c++11
New-ToString()
TPS=4086582.750000000
SStream-ToString()
TPS=518112.9062500000
TPS=1592562.3750000000
old-ToString()
TPS=2909644.5000000000
snprintf
速度较慢。它至少需要性能,就像
old-ToString
#include <cmath>
#include <strtk.hpp>
#include <iostream>
using namespace std;

int main ( int argc, char **argv ) 
{
   double pi = M_PI;
   std::cout << strtk::type_to_string<double>( pi ) << std::endl;
   return 0;
}