`
emowuyi
  • 浏览: 1481924 次
文章分类
社区版块
存档分类
最新评论

自己动手写C语言浮点数转换字符串函数

 
阅读更多

前几天,应一个小友要求,写了几个字符串转换函数帮助其进行语言学习,自觉其中的几个函数还比较满意,故发布在此,可供初学者参考。

浮点数转换字符串函数说简单也简单,说麻烦,也够烦心的,关键看你如何写了。简单点的几十行代码就行,复杂点的恐怕就的几百行代码了。如果还要考虑移植性、可读性甚至可维护性等就更麻烦的了。我一贯认为,一些事务性的项目应着重考虑移植性、可读性和可维护性等,而常用的带点系统性质的函数代码就应该以执行效率为主。

本文的浮点数转换字符串函数还是比较复杂的,基本可算得上较低层次的转换。由于我已经习惯了用BCB写C/C++代码,因此我写的浮点数转换字符串函数是80位扩展精度浮点数的,但那个小友拿回去试了一下,说他用的VC不支持80位扩展精度浮点数,虽然能定义long double变量,但实际上还是64位的,我只好又重写了一个64位双精度浮点数的,2个版本使用条件编译,这也算得上是移植性吧,呵呵。

下面是浮点数转换字符串函数的全部代码:

2个版本的代码加起来很长,但还有个自写的springf函数(下篇文章开始介绍)也要用到本文除FloatToSt函数外的全部代码。

代码开头的USE_EXTENDED为编译条件,如果你的编译系统不支持80位扩展精度浮点数,可将该定义注释掉。

前面说了,由于该代码主要是学习用的,因此数据转换层次较低,涉及到的有关浮点数格式的知识,可在网上搜索到。当然,知道是一回事,而具体怎样去操作则又是另一回事了,一些关键地方,我都作了较详细的注释,相信能对初学者正确理解浮点数格式有所帮助。例如,如何在不调用C有关函数,不使用汇编而快速的求一个浮点数的绝对值?本文代码就直接对浮点数进行操作:*((LPBYTE)&val + 7) &= 0x7f;(双精度浮点数)和*((LPBYTE)&val + 9) &= 0x7f;(扩展精度浮点数),也就是直接将浮点数的最高位置零,这当然比什么if (val < 0) val = -val语句快多了。不过,如果你要说后者的可移植性好,那我就无话可说了。要说可移植性,前者也可办到的,修改一下:*((LPBYTE)&val + sizeof(val) - 1) &= 0x7f;不就行了么,除非浮点数格式规则改变。只不过本文代码主要用来学习,用显式的方式更有意义。

80位扩展精度浮点数的有效数字为19位,而64位双精度浮点数有效数字为15 - 16位,本文的解析函数FloatResolve分别用了19位和17位的最大转换精度,尽可能的多显示几位,这主要是为自写的sprintf函数(另文介绍)做准备的,本文的浮点数转换字符串函数FloatToStr只用了最大15位的精度。

下面是个很简单的调用例子:


再次声明:本文代码主要供学习使用,如作其它用途,出问题慨不负责。

水平有限,错误在所难免,欢迎指正和指导。邮箱地址:maozefa@hotmail.com


分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics