use*_*710 11 c c++ assembly trigonometry intel
由于在x86下fsin计算sin(x)函数的函数可以追溯到Pentium时代,显然它甚至没有使用SSE寄存器,我想知道是否有更新更好的指令来计算三角函数.
我习惯用C++编写代码并做一些asm优化,所以任何适合从C++开始,到C语言到asm的管道都适合我.
谢谢.
我现在处于Linux 64位以下,gcc并且clang(甚至强硬的铿锵并没有提供任何与FPU相关的优化AFAIK).
编辑
sin功能,它通常是2倍于std::sin甚至sse上.fsin,即使很难fsin通常更准确,但考虑到fsin从未超越我的sin实现,我将保留我sin的现在,也是我sin完全可移植的fsin只有x86.Pas*_*uoq 11
如果需要近似的正弦优化绝对精度超过-π...π,请使用:
X*(1 + X*X*(-0.1661251158026961831813227851437597220432 + X*X*(8.03943560729777481878247432892823524338e-3 + X*X*-1.4941402004593877749503989396238510717e-4))
它可以用以下方式实现:
float xx = x * x;
float s = x + (x * xx) * (-0.16612511580269618f + xx * (8.0394356072977748e-3f + xx * -1.49414020045938777495e-4f));
Run Code Online (Sandbox Code Playgroud)
并且可能根据目标架构的特性进行优化.此外,在链接的博客文章中没有注明,如果您在汇编中实现此功能,请使用该FMADD说明.如果使用C或C++实现,如果使用fmaf()C99标准函数,请确保FMADD生成.模拟版本比乘法和加法要昂贵得多,因为fmaf()它不是完全等同于乘法后加法(所以如此实现它是不正确的).
sin(x)与-π和π之间的上述多项式之间的差异如下:

优化多项式以减少它与-π和π之间的sin(x)之间的差异,而不仅仅是某人认为是个好主意的东西.
如果您只需要[-1 ... 1]定义间隔,则可以通过忽略其余部分使该多项式在该间隔上更准确.再次为此定义间隔运行优化算法会产生:
X*(1 + X*X*(-1.666659904470566774477504230733785739156e-1 + X*X*(8.329797530524482484880881032235130379746e-3 + X*X*( - 1.928379009208489415662312713847811393721e-4)))
绝对错误图:

如果这对您来说太准确,则可以针对相同的目标优化较低程度的多项式.那么绝对误差会更大,但你会保存乘法或两次.
如果你没有接近(我假设你是,如果你想要击败硬件),你应该看看Nick sin在DevMaster上的实现:
http://devmaster.net/posts/9648/fast-and-accurate-sine-cosine
他有两个版本:"快速和草率"方法和"慢速和准确"方法.一对夫妇回复某人估计相对误差分别为12%和0.2%.我自己完成了一个实现,并在我的机器上找到了1/14和1/8硬件时间的运行时间.
希望有所帮助!
PS: 如果你自己这样做,你可以重构缓慢/准确的方法,以避免乘法,并略微改善尼克的版本,但我不记得究竟如何...