复数的话我就写sin,cos了
我只想知道x很大很大的时候怎么算比较快 简单的说说我的想法,当e很小的时候,接近于0, 计算e^x,可用泰勒公式求解,这个就不多说了。我这了说说如何将计算 $e^y$转化为$e^x$的算法过程,y是任意正实数,x是一个非常接近于0的数。
1.首先准备一个对数张,这个表格包含2列,第一列是一个数,第二列是这个数的自然对数,如
'10/9
0.105360515658
'9/8
0.117783035656
'6/5
0.182321556794
'5/4
0.223143551314
'4/3
0.287682072452
'3/2
0.405465108108
'8/5
0.470003629246
'5/3
0.510825623766
'9/5
0.587786664902
2
0.693147180560
'20/9
0.798507696218
'9/4
0.810930216216
'12/5
0.875468737354
'5/2
0.916290731874
'8/3
0.980829253012
3
1.098612288668
4
1.386294361120
5
1.609437912434
6
1.791759469228
8
2.079441541680
9
2.197224577336
10
2.302585092994
容易看出,只要计算出2,3,5这3个小质数的对数,就可以很容易求出上面这个表,当然你可以使用更多的质数的对数,得到表项(更密集)更多的表。
下面我们我们说一下,如何利用这个表,来计算e^x , 我们 以 r= e ^ 2008.12151318 为例来说明计算过程
1.2008.12151318大于表的最后一个表项log(10), 用 2008.12151318/log(10) ,得到整数部分872,尾数0.2673120891921=2008.12151318-ln(10)*872
则 r= e ^ 2008.12151318 =10^872 * e^0.2673120891921
2. 对 0.2673120891921 ,我们查表的得到log(5/4)=0.2231435513142, 因此有
r=10^872 * 5/4 * e^(0.2673120891921-0.2231435513142)
=10^872 * 5/4 * e^0.0441685378779
此时,0.0441685378779非常小了,很容易利用泰勒公式得到。
如果你觉得这个值利用泰勒公式收敛的还是有点慢,那么你可以使用更多的小质数的对数,制造一个含有更多表项的对数表。
[ 本帖最后由 liangbch 于 2008-12-15 14:54 编辑 ] liangbch我在考虑
是否有个只用单精度计算
就能得到对数的32位十进制数值的
方法
如果按你上面的方法
是否只要有一些小质数的精确到48位数的10的对数值
能否以很快的方法得到16位整数的精确到32位的10的对数
回复 63# liangbch 的帖子
流程中第一步推导有误!$r=e^2008.12151318 = e^{872.11609216528*ln(10)} $
$ = (e^ln(10))^872.11609216528 = 10^{872 + .11609216528}$
$ = 10^.11609216528 xx 10^872$
也就是说,经过换底公式后,就不再存在以 $e$ 为底的指数运算了。
回复 65# gxqcn 的帖子
63楼 的确有问题,谢谢指正。现在63#的步骤已经更正。
回复 64# 无心人 的帖子
对于32有效数字的对数计算,完全使用系统提供的数据类型仍然不可行。你需要实现1.多精度加减法
2.多精度 乘以/除以 单精度的乘除法。 恩
明白了
你分析过终止条件么?
懒得分析
呵呵
另外,呵呵
完全用2的对数迭代
和用一个8位的数字的对数迭代
比如99999999的对数迭代
哪个效果好? 原帖由 无心人 于 2008-12-15 15:17 发表 http://bbs.emath.ac.cn/images/common/back.gif
恩
明白了
你分析过终止条件么?
懒得分析
呵呵
另外,呵呵
完全用2的对数迭代
和用一个8位的数字的对数迭代
比如99999999的对数迭代
哪个效果好?
不明白你的意思? to liangbch:
既然已经通过换底公式将底数换成了10,
那何不接下来就一直在10进制下计算乘幂?
我的意思是 10^x (0<x<1) 也可直接去计算吧?
犯不着再倒回到以 e 为底的指数运算,
多一道工序多一些潜在精度损失,除非是为了适应算法需要。