天文年历或其它出版物中包含了一些数值表,这些表是等间距离的x对应的y的值。如y是太阳的赤经,x是该年各天的0时(TD)
插值是在表中寻找某个量(x或y)的中间值的过程。比如数据表中只给出某几个时刻的y值,要求其它时刻的y值就需考虑使用插值方法。
当然,刚才说的表不一定取自某一本书,也可以来正某个程序。假设在同一天内,已计算出了多个时刻(>3)的太阳位置,比例我们算出某天0h、12h和24h的太阳位置,然后利用这些值为其它给定的时刻执行“插值计算”,进而得到相应的太阳位置,这将比直接计算太阳位置快得多。
本章将考虑两种情况:3点插值和5点插值。这两种情况下,我们都将展示如何寻找函数的极值或零值。我们不考虑只有2点的插值,这种插值是线性的,一点也不困难。
◆ 三列表值(三节点插值)
函数的列表值y1、y2、y3对应的x的值为x1、x2、x3,再让我们看如下差分表:
x1 y1 a x2 y2 c (3.1) b x3 y3 式中a=y2-y1,b=y3-y2,称为一阶差分。二阶差分为c=b-a,即:c = y1 + y3 - 2*y2
通常逐次差分的值会逐渐变小。当表中的某一部分的二次差为常数(即三次差分为0),就应使用三节点插值。这时还需要有一些常识和经验,例如,月亮的位置可以用每小时间隔的三点插值计算,但间隔1天则不行。
例如,让我们考虑1992年11月5日至9日(每天的0h TD)火星到地球的距离。距离使用天文单位,差分值使用0.000001天文单位:
1992年11月5 0.898013 -6904 6 0.891109 +21 -6883 +2 7 0.884226 +23 -6860 +2 8 0.877366 +25 -6835 9 0.870531 三阶差分已几乎为零,我们可以使用三节点插值。
中间节点x2应选在靠近我们要插值的x附近。例如,如果要用上表推算11月7日22h 14m的函数值,那么上表中11月8.00的值定为y2,因此我们考虑插值节点为11月7、8、9日,即:
11月7日 y1 = 0.884226 11月8日 y2 = 0.877366 (3.2) 11月9日 y3 = 0.870531
差分值为:a = -0.006860 b = -0.006835 c = +0.000025
设n是插值因子。如果函数值y是关于x参数的,那么n = x - x2,单位是节点的间隔。当x>x2时(即x的值在x2到表底之间)n为正。如果x在x2之前,那么n<0。
当正确选则了y2,那么n将在-0.5到0.5之间,虽然n在-1到1之间以下公式仍然可以得到正确结果。
y = y2 +(n/2)( a + b + nc ) (3.3)
例3.a: 从表(3.2),计算1992年11月8日4h 21m TD时的火星到地球的距离。我们有4h 21m = 4.35小时,表中的节点间隔为1天=24小时,所以:
n = 4.35/24 = +0.18125
由公式(3.3)得 y = 0.876125
·极值
如果列表值在极值(最大值或最小值)附近,通过以下方法可找到极值。让我们从差分表(3.1)是取得适当的部分星历,那么函数的极值是:
ym = y2 - (a+b)2/(8c) (3.4)
对应的x值是:
nm = -(a+b)/(2c) (3.5)
单位是表间隔,同样是从x2开始测量的。
例3.b:计算1992年5月火星经过近日点的时刻及距离。以下是每间隔4天太阳到火星的距离:
1992年5月 12.0 TD 1.3814294 1992年5月 16.0 TD 1.3812213 1992年5月 20.0 TD 1.3812453
差分值为:a = -0.0002081 b = +0.0000240 c = 0.0002321
进而得到:ym = 1.3812030 和 nm= +0.39660
因此,火星到太阳的最近距离是1.3812030AU,对应的时刻是0.39660乘以4天(列表值的时间间隔),即1.58640天,也就是在中点时刻之后1天14小时,相应的时间是1992年5月17日14h TD。
当然,如果nm是负值,极值时刻则在中点时刻之前。
·插值逆求
选择(3.1)差分表中的适当部分星历,我们可以计算出函数值y=0时对应的x值。下式可算出函数值为0时的插值因子:
no = -2y2/(a + b + cno) (3.6)
解方程(3.6)时,可先用no=0代入方程右边,得到no的估值。这个估值再次代入方程的右边,将得到精度更好的no。这个过程叫做“迭代”(拉丁语:iterare = 重复),我们可以返复迭代,直到no的值不再变化,到达计算机的精度。
例3.c:以下是水星的赤纬:
1973年2月 26.0 TD -0°28'13".4 1973年2月 27.0 TD +0°06'46".3 1973年2月 28.0 TD +0°38'23".2
试计算赤纬为零的时刻。
先把列表值转为角秒单位并建立差分表:
y1 = -1693.4 a = +2099.7 y2 = + 406.3 c = -202.8 b = +1896.9 y3 = +2303.2 由公式(3.6)得:no = -812.6/(+3996.6 - 202.8no)
把 no = 0 代入方程右边,得:no = -0.20332
重复计算,依次得到:-0.20125和-0.20127。因此,no = -0.20127。又因列表间隔为1天,所以水星穿过天赤道时间在:
1973年2月27.0 - 0.20127 = 2月 26.79873 = 2月26日19h 10m TD
计算函数值y为零时的插值因子no时,例3情形下,使用公式(3.6)效果非常好,因为此时的函数曲线几为是一条直线。然而,如果函数的曲率很大,使用该公式可能需要迭代很多次,此外,即使no的起步值比较精确也可能导致分歧。在这种情况下,可以使用以下更好的方法计算no,估计值no的修正量为:
Δno = -[ 2y2+no(a+b+cno) ]/(a +b + 2cno) (3.7)
用新的no重量复迭代计算,直到no不再变化。
例3.d:——考虑以下函数值:
x1 = -1 y1 = -2
x2 = 0 y2 = +3
x3 = +1 y3 = +2
这三个点其实定义了一条抛物线:y = 3 + 2x - 3x^2,在x=-1到x=+1之间,它的曲率很大,见下图:
利用公式(3.6),从no=0开始迭代,结果依次是: -1.5 -0.461538... -0.886363... -0.643902... -0.763027... -0.699450... ... 需要至少24次迭代才能到6位有效数字。但如果我们使用公式(3.7),同样起步为no=0,我们得到: -1.5 -0.886363636364 -0.732001693959 -0.720818540935 -0.720759221726 -0.720759220056 -0.720759220056 只需6次迭代就得到了12位精度。
◆ 五列表值(5节点插值)
当三阶差分不可忽略时,应必须使用多于3列表值。取连续的5个列表值y1到y5,和前面一样,我们创建差分表:
y1 A y2 E B H n
y3 F K ↓
C J y4 G D y5 其中 A = y2 - y1,H = F - E,等等。如果n是插值因子,从y3开始测量,单位是表值的间隔,向下(y4方向)为正,则插值公式为:
例3.e:——考虑下表,月球的赤道水平视差:
1992年2月 27.0 TD 54'36".125 1992年2月 27.5 54'24".606 1992年2月 28.0 54'15".486 1992年2月 28.5 54'08".694 1992年2月 29.0 54'04".133
A =-11.519 E = +2.399 B = -9.120 H = -0.071 F = +2.328 K = -0.026 C = -6.792 J = -0.097 G = +2.231 D = -4.561 我们看到,三阶差分(H和J)不可以忽略,除非精度要求0".1就已足够。
现在让我们计算2月28日2h 20m TD时月亮的是视差。列表值的间隔是12小时,所以有: n = (3h 20m)/12h = 3.333333/12 = +0.2777778
由公式(3.8)得: y = 54'15".486 - 2".117 = 54'13".369
函数的极值对应的插值因子nm可通过解以下方程得到:
和上面的一样,我们可以执行迭代。首次,把 nm = 0 代入方程右边。当我们最后得到nm后,再通过(3.8)式得到相应的函数值。
最后,函数值为零时对应的插值因子no可由下式得到:
同样,可以通过迭代得到no,起步为no=0。
同公式(3.6)遇到同样的问题,当函数的曲率较大时,应使用更好的方法计算no,方法如下:
接下来,用新的no代入右边计算,如此重复,直到no不再变化。
练习:以下是水星的日心黄纬,请用公式(3.10)计算黄纬为0的时刻。
1988年1月25.0 TD -1°11'21".23 1988年1月26.0 TD -0°28'12".31 1988年1月27.0 TD +0°16'07".02 1988年1月28.0 TD +1°01'00".13 1988年1月29.0 TD +1°45'46".33
答案:水星经经过其轨道升交点时,no = -0.361413,即1988年1月26.638587,或者写为:1月26日 15h 20m TD 如果使用公式(3.6)得到 no = -0.362166,与前面的比较,相差0.000753日(1.1分钟)
重要注意事项:
1、执行插值时,不能直接使用“复合”量。这些量应事先转为单一的适合的单位。便如:角度表达为度分秒格式,在使用插值前,应把它们转为同一单位“度”(或者分或者秒)。 注:根据定义,“复合”数是指由不单位组成的数,如以下几个都是“复合”数:10h 29m 55s;23°26'44";先令,便士;码,英尺,英寸;a+bi。
2、时间插值与赤经。——我们应当引起注意一个事实,当到达24小时,赤经跳为0。在使用列表值进行插值时必须考虑到这一点。例如,假设我们要计算1992年4月6.2743 TD时刻水星的赤经,使用以下3个值:
1992年4月5.0 TD α=23h 51m 56s.04 1992年4月6.0 TD 23h 56m 28s.49 1992年4月7.0 TD 00h 01m 00s.71
不仅要把赤经转为带小数的小时数,还要把最后那个值写为24h 01m 00s.71,否则机器认为,从4月6.0到7.0,赤经α由23h56m...变到0h01m...
我们发现还有其它的类似情况。例如,以下是连续几天的太阳的中央子午圈经度:
1992年6月14.0 UT 37°.96 1992年6月15.0 24°.72 1992年6月16.0 11°.48 1992年6月17.0 358°.25
很明显,每天大约变化-13.24度。然而,但我们不能在11.48和358.25之间插值。应把前者写为271°.48,或者把后者写为-1.75度。
3、要尽可能避免插值在|n|>0.5。在任何情况下,插值因子应限制在-1到+1之间。计算函数极值点(nm)或零值点(no)也有同样的限制。应按这种方式选择中央的y:列表值应靠近极值或零值。当然,事先我们并不知道nm或no的准确值,但我们可以先算出估计值,之后即可根据估值确定中央值(y3或y2)。
如果选择的值距离零点或极点太远,那么本章提供的相应公式将计算不正确,甚至是荒谬的结果。让我们给出一个例子。我们知道sin(x)在x=90度时达到最大值。但让我们考虑以下含有10位有效数字正弦值:
sin29° 0.4848096202 sin30° 0.5000000000 sin31° 0.5150380749 sin32° 0.5299192642 sin33° 0.5446390350
使用3节点插值,由公式(3.4)得 ym = 1.22827(而不是1),由(3.5)得到 nm = +95.35,即极值是 31° + 95°.35 = 126°.35,而不是90°. 使用5节点插值,由(3.9)式得 nm = +57.30,因此最大值位于88°.30,相应的极值是0.99348。虽然,这个结果比3节点插值要好得多,但仍然欠佳。
◆ 在中点插值
如果等间距横坐标x1、x2、x3、x4对应的函数值是y1、y2、y3、y4,那么x2到x3之间的中点对应的函数值为:
y = [ 9(y2+y3) - y1 - y4 ] / 16 (3.12)
3.f:——以下是月亮的视赤经:
1994年3月25日 08h TD α=10h 18m 48s.732 1994年3月25日 10h TD 10h 23m 22s.835 1994年3月25日 12h TD 10h 27m 57s.247 1994年3月25日 14h TD 10h 32m 31s.983
试计算 11h 00m TD 时刻的赤经。
把10h后面的分秒转化“秒”单位,得:
y1 = 1128.734秒 y2 = 1402.835 y3 = 1677.247 y4 = 1951.983
由公式(3.12)得 y = 1540.001秒 = 25m 40s.001,所以要求的赤经是α=10h 25m 40s.001。
◆ 横坐标不等间距插值公式:拉格朗日插值公式
当给定的横坐标值(即x的值)是不等间距的,可以使用拉格朗日插值公式。当然,该公式也可以用于等间距的情况下。
这个简单的公式由法国数学家拉格朗日发现,它使用n个点拟合一个n-1次的多项式。如果给定的点是(xi,yi),i=1到n,那么对于给定的x,公式如下:
要注意的是,所有的xi须是不同的点。
以下BASIC程序可以使用。
10 DIM X(50),Y(50) 20 PRINT "NUMBER OF GIVEN POINTS = "; 30 INPUT N 40 IF N<2 OR N>50 THEN 20 50 PRINT 60 FOR I=1 TO N 70 PRINT "X,Y FOR POINT No."; 80 INPUT X(I),Y(I) 90 IF I=1 THEN 30 100 FOR J=1 TO I-1 110 IF X(I)=X(J) THEN PRINT "THIS VALUE OF X HAS ALREADY BEEN USED!":GOTO 70 120 NEXT J 130 NEXT I 140 PRINT : PRINT "POINT X FOR INTERPOLATION = "; 150 PRINT Z 160 V=0 170 FOR I=1 TO N 180 C=1 190 FOR J=1 TO N 200 IF J=I THEN 220 210 C=C*(Z-X(J))/(X(I)-X(J)) 220 NEXT J 230 V=V+C*Y(I) 240 NEXT I 250 PRINT : PRINT "INTERPOLATED VALUE = ";V 260 PRINT : PRINT "STOP(0) OR INTERPOLATION AGAIN(1)"; 270 INPUT a 280 IF A=0 THEN STOP 290 IF a=1 THEN 140 300 GOTO 260
程序选请求你要输入的数据点的个数,并立刻让你输入。然后重复请求你感兴趣的中间值(x的值),程序返回每个插值。
拉格朗日插值的一个显著特征是,不要求点数据是按顺序的,也不要求等间距。间距均匀时精度比较高。
作为一个例子,用以下6点数据调试程序:
x=角度(单位:度) y=sin(x) 29.43 30.97 27.69 28.11 31.58 33.05 0.491 359 8528 0.514 589 1926 0.464 687 5083 0.471 165 8342 0.523 688 5653 0.545 370 7057 当请求30度时的正弦值,可得到精确值0.5。当x=0度或x=90度时,使用以上6个数据结合拉格朗日插值公式仍然可以得到很好的结果:+0.0000482和+1.00007,对应的正确值是0和1。
表达式(3.13)是一个n-1阶的多项式,这是利用y1、y2……yn所能得到的唯一的一个n-1阶多项式(注:多项式插值具有唯一性)。但拉格朗日公式本身有个缺点,就是没有给出所需的数据点数量,以争取达到理想的精度。不过,当我们希望表达一个函数的明确的插值多项式是,而x又远离插值节点,那么使用拉格朗日公式是有益的。
例3.g:——使用以下数据构造一个(唯一的)3次多项式: