如何仅用C语言的double实现128位浮点/定点数模拟及运算函数?
基于double模拟128位浮点数的运算实现
模拟类型定义
用两个double拆分存储:高位存主要有效数值,低位存残差补偿,结构如下:
typedef struct { double hi; // 高64位有效部分 double lo; // 低64位残差补偿 } Float128;
初始化说明
- 英文说明:Set
hito your base input value (cast to double if needed). Computeloas the residual between the original high-precision value andhifor better initial precision; setlo = 0if basic initialization is sufficient. - JavaScript示例:
function createFloat128(input) { const hi = Number(input); const lo = input - hi; // Capture leftover precision return { hi, lo }; }
核心运算函数(优先速度,允许精度损失)
加法
Float128 float128_add(Float128 a, Float128 b) { Float128 res; const double sum_hi = a.hi + b.hi; const double sum_lo = ((a.hi - sum_hi) + b.hi) + (a.lo + b.lo); res.hi = sum_hi + sum_lo; res.lo = sum_lo - (res.hi - sum_hi); return res; }
基于双精度加法残差补偿,速度接近原生double运算。
减法
Float128 float128_sub(Float128 a, Float128 b) { Float128 res; const double diff_hi = a.hi - b.hi; const double diff_lo = ((a.hi - diff_hi) - b.hi) + (a.lo - b.lo); res.hi = diff_hi + diff_lo; res.lo = diff_lo - (res.hi - diff_hi); return res; }
仅对加法逻辑做符号调整,保持运算效率。
乘法
Float128 float128_mul(Float128 a, Float128 b) { Float128 res; // 忽略低-低乘积项,以精度换速度 const double ab = a.hi * b.hi; const double cross = a.hi * b.lo + a.lo * b.hi; res.hi = ab + cross; res.lo = cross - (res.hi - ab); return res; }
除法
Float128 float128_div(Float128 a, Float128 b) { Float128 res; double q = a.hi / b.hi; // 一次牛顿迭代修正商值,平衡速度与精度 const double r_hi = a.hi - q * b.hi; const double r_lo = a.lo - q * b.lo; const double correction = (r_hi + r_lo) / b.hi; res.hi = q + correction; res.lo = (r_hi - (res.hi - q)*b.hi) + r_lo; return res; }
转换为float的方法
直接合并高低位后转换,或仅取高位(精度稍低但更快):
float float128_to_float(Float128 val) { // 合并后转换,精度更优 return (float)(val.hi + val.lo); // 仅取高位,速度更快 // return (float)val.hi; }
扩展:192/256位模拟方案
192位浮点数(3个double)
typedef struct { double hi; double mid; double lo; } Float192;
运算逻辑:从高位到低位依次计算,每步保留残差传递到下一级;乘法/除法仅保留前两级交叉项,牺牲最低位小项以保证速度。
256位定点数(4个double)
typedef struct { double int_hi; // 整数部分高位 double int_lo; // 整数部分低位 double frac_hi; // 小数部分高位 double frac_lo; // 小数部分低位 } Fixed256;
定点数运算速度远快于浮点模拟,加减按位对齐后直接运算,乘法拆分四部分合并,适合对速度要求极高、可接受数值范围限制的场景。
内容的提问来源于stack exchange,提问作者Infigon
相关产品推荐
相关产品推荐

