首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >AnsiString到双C++

AnsiString到双C++
EN

Stack Overflow用户
提问于 2017-12-30 14:22:22
回答 3查看 3.5K关注 0票数 1

我正在尝试将一个AnsiString转换为一个double,但是在运行程序之后,它会说"20.60不是一个有效的浮点“。

代码语言:javascript
复制
AnsiString Temperatur

RE_Temperatur->Text = Temperatur;

Chart1->Series[0]->AddXY(DT_Uhrzeit->Time, RE_Temperatur->Text.ToDouble(), 
"", clRed);

Temperatur的值来自来自我的Arduino的SerialPort连接,并提供了20.60之类的内容。当我将字符串切到前2位时,它工作得很好。我猜.与错误有关,但我不知道如何解决它。

编辑//我现在尝试只替换“”。使用",“的代码如下:

代码语言:javascript
复制
    RE_Temperatur->Text = StringReplace(RE_Temperatur->Text, ".", ",", 
    TReplaceFlags() << rfReplaceAll);

现在我得到一个错误消息"20,60不是一个有效的浮点“。这太令人沮丧了

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2018-01-03 13:22:57

在一个新的控制台程序中尝试这段简单的代码:

代码语言:javascript
复制
AnsiString Temperatur = "12.45"; // locale independent
AnsiString Temperatur2 = "12,45"; // correct in my German locale

double temp = StrToFloat(Temperatur, TFormatSettings::Invariant());
double temp2 = StrToFloat(Temperatur2); // In my case: German locale!

printf("%8.4f %8.4f\n", temp, temp2);

产出如下:

代码语言:javascript
复制
 12.4500  12.4500

您可以看到它如预期的那样工作。请注意,在我的系统中,逗号是区域设置的十进制分隔符,但是由于格式设置不变,这段代码在句点作为小数分隔符时可以很好地工作。

因此,做出选择:如果需要独立于区域设置,则使用TFormatSettings::Invariant(),但如果您希望它对用户的区域设置使用十进制分隔符,则不要使用它。

票数 2
EN

Stack Overflow用户

发布于 2017-12-31 06:39:08

您可以使用StrToFloat,它有第二个版本,它接受一个TFormatSettings对象,您可以使用它来指定一个特定的DecimalSeperator。顺便说一句,它不返回浮点数,因为它的名称可能意味着它返回一个Extended,又名long double

票数 2
EN

Stack Overflow用户

发布于 2017-12-31 10:59:04

我打赌你的问题是小数点。它所使用的字符是Windows环境变量之一,可随计算机而异。有人打电话来接,但我不记得了.

AnsiString("1.23").ToDouble()的问题是,catch/try不会捕获异常(至少在我的编译器BDS2006上是这样)。有解决办法。我使用的是atoi(),它不是崩溃,而是在出现无效字符时截断为整数,因此可以用来检测正确的小数点字符和转换:

代码语言:javascript
复制
char _floating_point_char=' ';         // decimal point separator
AnsiString   strnum (AnsiString s,int sig=1,int pnt=1,int hex=0,char dot=_floating_point_char);
double       str2num(AnsiString s,int sig=1,int pnt=1,int hex=0,char dot=_floating_point_char);

AnsiString strnum(AnsiString s,int sig,int pnt,int hex,char dot)
    {
    if (dot==' ')
        {
        float x;
        x=atof("0.5"); if (x>=0.25) _floating_point_char='.';
        x=atof("0,5"); if (x>=0.25) _floating_point_char=',';
        dot=_floating_point_char;
        }

    int i,l,a,e,e0,exp=pnt;
    AnsiString q="";
    l=s.Length();
    if (hex) exp=0;     // exponent is e,E so it colide with hex e,E
    e0=0; for (i=1;i<=l;i++)
        {
        e=0;
        a=s[i];
        if ((a>='0')&&(a<='9'))       { e=1; q+=char(a  ); sig=0; }
        if ((a>='A')&&(a<='F'&&(hex))){ e=1; q+=char(a  ); sig=0; }
        if ((a>='a')&&(a<='f'&&(hex))){ e=1; q+=char(a  ); sig=0; }
        if ((a=='e')||(a=='E'))
         if (!hex)   { if (!exp) break; e=1; q+=char('e'); exp=0; sig=1; pnt=0; e0=0; }
        if (a=='+')  { if (!sig) break; e=1;               sig=0; }
        if (a=='-')  { if (!sig) break; e=1; q+=char(a  ); sig=0; }
        if (a=='.')  { if (!pnt) break; e=1; q+=char(dot); pnt=0; }
        if (a==',')  { if (!pnt) break; e=1; q+=char(dot); pnt=0; }
        if ((e0)&&(!e)) break;
        e0|=e;
        }
    if (q.Length()<=0) q="0";
    return q;
    }
double str2num(AnsiString s,int sig,int pnt,int hex,char dot)
    {
    return atof(strnum(s,sig,pnt,hex,dot).c_str());
    }

它只需检测.,是否是正确的,然后在转换前用字符串替换它.从winapi中粗取正确的小数点字符,更安全,因为小数点分隔符可以是任何东西。你可以忽略hex部分--我用它做任何数字.

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/48034799

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档