Go 语言函数式编程系列教程(五) —— 数据类型篇:浮点型与复数类型

栏目: PHP · 发布时间: 5年前

内容简介:浮点型也叫浮点数,用于表示包含小数点的数据,比如和 PHP 一样,Go 语言中的浮点数采用在 Go 语言里,定义一个浮点数变量的代码如下:

浮点型

浮点型也叫浮点数,用于表示包含小数点的数据,比如 3.141.00 都是浮点型数据。

浮点数的表示

PHP 一样,Go 语言中的浮点数采用 IEEE-754 标准的表达方式,定义了两个类型: float32float64 ,其中 float32 等价于 PHP 的 float 类型(单精度浮点数),可以精确到小数点后 7 位, float64 等价于 PHP 的 double 类型(双精度浮点数),可以精确到小数点后 15 位。

Go 语言里,定义一个浮点数变量的代码如下:

var float_value_1 float32

float_value_1 = 10
float_value_2 := 10.0 // 如果不加小数点,float_value_2 会被推导为整型而不是浮点型
float_value_3 := 1.1E-10

对于浮点类型需要被自动推导的变量,其类型将被自动设置为 float64 ,而不管赋值给它的数字是否是用 32 位长度表示的。因此,对于以上的例子,下面的赋值将导致编译错误:

float_value_1 = float_value_2  // float_value_2 是 float64 类型

编译错误信息如下:

cannot use float_value_2 (type float64) as type float32 in assignment

必须使用这样的强制类型转换才可以:

float_value_1 = float32(float_value_2)

在实际开发中,应该尽可能地使用 float64 类型,因为 math 包中所有有关数学运算的函数都会要求接收这个类型。

浮点数的精度

浮点数不是一种精确的表达方式,因为二进制无法精确表示所有十进制小数,比如 0.10.7 这种,下面我们通过一个示例来给大家直观演示下:

float_value_4 := 0.1
float_value_5 := 0.7
float_value_6 := float_value_4 + float_value_5

注:浮点数的运算和整型一样,也要保证操作数的类型一致, float32float64 类型数据不能混合运算,需要手动进行强制转化才可以,这一点和 PHP 不一样。

你觉得上面计算结果 float_value_6 的值是多少?0.8?不,它的结果是 0.7999999999999999 ,这是因为计算机底层将十进制的 0.10.7 转化为二进制表示时,会丢失精度,所以永远不要相信浮点数结果精确到了最后一位,也永远不要比较两个浮点数是否相等。

浮点数的比较

浮点数支持通过算术运算符进行四则运算,也支持通过比较运算符进行比较(前提是运算符两边的操作数类型一致),但是涉及到相等的比较除外,因为我们上面提到,看起来相等的两个十进制浮点数,在底层转化为二进制时会丢失精度,因此不能被表象蒙蔽。

如果一定要判断相等,下面是一种替代的解决方案:

p := 0.00001
// 判断 float_vlalue_1 与 float_value_2 是否相等
if math.Dim(float64(float_value_1), float_value_2) < p {
    fmt.Println("float_value_1 和 float_value_2 相等")
}

可以看到,我们的解决方案是一种近似判断,通过一个可以接受的最小误差值 p ,约定如果两个浮点数的差值在此精度的误差范围之内,则判定这两个浮点数相等。这个解决方案也是其他语言判断浮点数相等所采用的通用方案,PHP 也是这么做的。

复数类型

除了整型和浮点型之外,Go 语言还支持复数类型,与复数相对,我们可以把整型和浮点型这种日常比较常见的数字称为实数,复数是实数的延伸,可以通过两个实数(在计算机中用浮点数表示)构成,一个表示实部(real),一个表示虚部(imag),常见的表达形式如下:

z = a + bi

其中 a、b 均为实数,i 称为虚数单位,当 b = 0 时,z 就是常见的实数,当 a = 0 而 b ≠ 0 时,将 z 称之为纯虚数,如果你理解数学概念中的复数概念,这些都很好理解,下面我们来看下复数在 Go 语言中的表示和使用。

在 Go 语言中,复数支持两种类型: complex64 (32位实部和虚部) 和 complex128 (64位实部与虚部),对应的表示示例如下,和数学概念中的复数表示形式一致:

var complex_value_1 complex64        

complex_value_1 = 1.10 + 10i          // 由两个 float32 实数构成的复数类型
complex_value_2 := 1.10 + 10i         // 和浮点型一样,默认自动推导的实数类型是 float64,所以 complex_value_2 是 complex128 类型
complex_value_3 := complex(1.10, 10)  // 与 complex_value_2 等价

对于一个复数 z = complex(x, y) ,就可以通过 Go 语言内置函数 real(z) 获得该复数的实部,也就是 x ,通过 imag(z) 获得该复数的虚部,也就是 y

复数支持和其它数字类型一样的算术运算符。当你使用 == 或者 != 对复数进行比较运算时,由于构成复数的实数部分也是浮点型,需要注意对精度的把握。

更多关于复数的函数,请查阅 math/cmplx 标准库的文档。如果你对内存的要求不是特别高,最好使用 complex128 作为计算类型,因为相关函数大都使用这个类型的参数。

号外:Go 语言研习社

昨天新建了一个「Go 语言研习社」,用于探讨交流 Go 语言学习和使用过程中的问题,免费加入,感兴趣的、或者正在学习 Go 语言的同学可以进来看看:

Go 语言函数式编程系列教程(五) —— 数据类型篇:浮点型与复数类型


以上所述就是小编给大家介绍的《Go 语言函数式编程系列教程(五) —— 数据类型篇:浮点型与复数类型》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

Code Reading

Code Reading

Diomidis Spinellis / Addison-Wesley Professional / 2003-06-06 / USD 64.99

This book is a unique and essential reference that focuses upon the reading and comprehension of existing software code. While code reading is an important task faced by the vast majority of students,......一起来看看 《Code Reading》 这本书的介绍吧!

RGB转16进制工具
RGB转16进制工具

RGB HEX 互转工具

MD5 加密
MD5 加密

MD5 加密工具

XML 在线格式化
XML 在线格式化

在线 XML 格式化压缩工具