divMod' 用于更快计算的替代方案

divMod' alternative for faster calculations

看起来 Data.Fixed 中的 divMod' 函数在我的测试中每次操作需要约 200ns(criterion x86 上的基准测试 Mac)。我所做的是在我编写的函数中禁用 divMod',然后比较前后的基准测试时间以得出净开销。启用 divMod' 后,该功能耗时 ~230ns,禁用时耗时 ~30ns。

我可以使用比 divMod' 更快的替代品吗?我也可以将它专门化为单一类型,例如 Double 以帮助加快速度。

环顾四周,但没有看到任何关于 'divMod'` 性能的提及。所以,在这里问一下。

我不能直接使用quotRem,因为我需要对double进行除法。

看起来库函数是这样定义的:

-- | Generalisation of 'div' to any instance of 'Real'
div' :: (Real a,Integral b) => a -> a -> b
div' n d = floor ((toRational n) / (toRational d))

-- | Generalisation of 'divMod' to any instance of 'Real'
divMod' :: (Real a,Integral b) => a -> a -> (b,a)
divMod' n d = (f,n - (fromIntegral f) * d) where
    f = div' n d

您可以将其调整为 Double 并以某种近似为代价对其进行简化:

divDouble :: Double -> Double -> Int
divDouble n d = floor (n / d)
{-#INLINABLE divDouble #-}

divDoubleMod :: Double -> Double -> (Int,Double)
divDoubleMod n d = (f,n - (fromIntegral f) * d) where
    f = divDouble n d 
{-#INLINABLE divDoubleMod #-}

希望 Double 除法比 Rational 上的原始除法更快,即使它更近似。