向量双双浮点运算

Posted

技术标签:

【中文标题】向量双双浮点运算【英文标题】:Vector double-double floating point arithmetic 【发布时间】:2019-04-19 08:57:36 【问题描述】:

存在双精度浮点不够充分的工作负载,因此需要四精度。这很少在硬件中提供,因此解决方法是使用双双,其中 128 位数字由一对 64 位数字表示。这不是真正的 IEEE-754 四倍精度 - 一方面,您不会获得任何额外的指数位 - 但在许多方面都足够接近,并且比纯软件实现要快得多。

许多计算机都提供向量浮点运算,最好将它们用于双双运算。这可能吗?特别是,在https://github.com/JuliaMath/DoubleDouble.jl/blob/master/src/DoubleDouble.jl 处查看 double-double 的实现,在我看来,每个算术运算都需要在中间至少有一个条件分支,我认为这意味着不能使用 SIMD 向量运算,除非我遗漏了什么?

【问题讨论】:

【参考方案1】:

我认为您正在考虑加法和减法的实现,例如:

# Dekker add2
function +T(x::DoubleT, y::DoubleT)
    r = x.hi + y.hi
    s = abs(x.hi) > abs(y.hi) ? (((x.hi - r) + y.hi) + y.lo) + x.lo : (((y.hi - r) + x.hi) + x.lo) + y.lo
    Double(r, s)
end

在某些架构上,解决方案可能是使用 SIMD 指令并行计算两个分支,然后执行一个操作来检索两个分支的正确结果。例如,通过从错误的操作数中减去 x.hi + y.hi 产生的错误结果可能总是有负号,因此取最大值可能总是会提取正确的结果。 (在这个晚上,我不能保证这在这种情况下是有效的,但对于某些操作,一般的做法是。)

另一个可能是比较向量x.hi, y.hi > y.hi, x.hi 以形成位掩码。 (这是伪代码,不是 Julia 语法。)位掩码和潜在结果对的按位与将保持正确结果不变,并将不正确的 1 的所有位设置为零。然后,使用按位或减少掩码向量会产生正确的结果。不需要分支。

给定的 ISA 可能还有其他可行的技巧,例如条件指令。或者还有除 Dekker 之外的其他算法。

【讨论】:

请注意,在实践中使用传统的 2sum 算法而不是 Dekker 的 Fast2Sum 可能更有效。传统的 2sum 可以有效地矢量化。例如,参见here:算法 1 和 2

以上是关于向量双双浮点运算的主要内容,如果未能解决你的问题,请参考以下文章

可靠地确定浮点值向量是不是(数字上)等距

如何通过频率来计算cpu的浮点运算能力滴?

java运算疑惑 整型和浮点型混合运算

FPU 浮点运算单元和DSP指令

使用浮点运算对整数数据进行右移运算?

JS 乘法运算出现了浮点,该怎么解决