Java中整数转浮点数的原理

参考

https://www.geeksforgeeks.org/ieee-standard-754-floating-point-numbers/

在JDK中Float,Double类中有一个方法

public static native float intBitsToFloat(int bits);
public static native long doubleToRawLongBits(double value);

原理

单精度浮点数在内存中的存储方式为:符号位(1bit)+指数(8bit)+尾数(23)
双精度浮点数在内存中的存储方式为:符号位(1bit)+指数(11bit)+尾数(52)

如图所示
在这里插入图片描述
在这里插入图片描述

当我们谈论浮点数的表示时,尤其是IEEE 754标准,指数部分(或称为“幂”或“指数”)是一个关键组成部分。IEEE 754标准规定了如何存储浮点数的三个部分:符号、指数和尾数(或称为分数或有效数字)。

为了理解为什么需要为实际指数添加一个偏差(bias),我们需要先了解为什么这样做。

  1. 为什么需要正负指数?
  • 在科学计数法中,一个数字可以表示为 ±a × 10^n 的形式,其中 a 是一个介于1到10之间的数(包括1但不包括10),而 n 是一个整数。n 可以是正数、负数或零。正指数表示数字被放大,而负指数表示数字被缩小。
  • 同样,在浮点数的二进制表示中,我们也需要能够表示正的和负的指数。
  1. 为什么需要添加偏差?
  • 为了简化硬件设计和提高精度,IEEE 754标准决定使用一个固定大小的字段来表示指数。例如,在单精度浮点数中,指数字段是8位,而在双精度浮点数中,它是11位。
  • 如果我们直接使用实际的指数值来存储,那么对于负数,我们需要一种方法来表示它。最简单的方法可能是使用补码表示法,但是补码对于负数需要求反码,然后加1。增加硬件设计的复杂性。整数的补码就是其本身。
  • 为了避免这种情况,IEEE 754标准决定为实际的指数值添加一个固定的偏差。这样,所有的指数值都会变为正数,从而简化了硬件设计和实现。
  • 例如,对于单精度浮点数,偏差是127。所以,如果实际的指数值是-1,存储的指数值将是126;如果实际的指数值是0,存储的指数值将是127;如果实际的指数值是1,存储的指数值将是128,依此类推。

总之,添加偏差是为了简化浮点数的存储和计算,尤其是在硬件实现中。它确保了我们总是使用正数来表示指数,从而避免了处理负数的复杂性。

特殊值

  • Zero(零)
  • 无穷大(包含正无穷大、负无穷大)
  • NAN(not a number)

当阶码全为 0:

  • 尾数 M 不全为 0 时,表示非规格化小数:±(0.xxx…xx)×2-126
  • 尾数 M 全为 0 时,表示真值 ±0

当阶码全为 1:

  • 尾数 M 全为 0:表示无穷大
  • 尾数 M 不全为 0:表示数值“NAN”,如0/0、∞-∞等

浮点数的 underflow(下溢)是指当一个接近于零的数值被当作零来处理的情况。

在计算机中,浮点数都是离散的、有限的。因此,计算机无法用有限的浮点数来表示无限的实数。在用浮点数表示实数时,很多数都会存在近似误差。其中一种是下溢(underflow)。比如,一个非常接近于零的数值A(实际上A>0),计算机会直接把该数值判为零,虽然实际上它并不为零。
源码实现

JNIEXPORT jint JNICALL
Java_java_lang_Float_floatToRawIntBits(JNIEnv *env, jclass unused, jfloat v)
{
    union {
        int i;
        float f;
    } u;
    u.f = (float)v;
    return (jint)u.i;
}

这段代码使用了一个联合体(union),这是一个特殊的数据结构,可以存储不同的数据类型,但是使用的内存是重叠的,因此在同一时间只能存储其中一个值。这里联合体用于将 jfloat 类型的值转换为 jint 类型的值,并直接返回这个值。

  • 23
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值