对于家庭作业,我必须编写一个函数,该函数提供余弦函数的乘积近似值,该函数递归直到当前和新计算的乘积之间的差值小于阈值。
(define (p_cos x)
(let* ([n 1]
[xnew (* x (p_cos_aux x (+ n 1)))])
(if (< (abs (- x xnew)) TOL)
x
(p_cos_aux xnew (+ n 1)))))
(define (p_cos_aux x n)
(- 1 (/ (* 4 (square x)) (* (square pi) (square (- (* 2 n) 1))))))
这些值预计是:
(p_cos 0)
=> 1
(p_cos (/ pi 2))
=> 0
但是我得到了:
> (p_cos (/ pi 2))
0.9122085048010974
> (p_cos 0)
0
任何人都可以向我解释为什么我的输出远离预期值?
我将我的代码基于这个无限乘积公式,用于近似余弦:
cos(x)=Πn= 1n→[[1 - (4x2)/(22(2n - 1)2)
因为你基于这个数学公式:
cos(x)=Πn= 1n→[[1 - (4x2)/(22(2n - 1)2)
看起来你的p_cos_aux
函数正在处理公式中方括号内的东西。所以你仍然需要将余弦定义为等于
cos(x)=Πn= 1n→∞(p_cos_aux x n)
如果您希望代码返回答案,那么您应该只为有限数量的n
执行此操作。您可以使用递归或for循环执行此操作。在这种情况下,Racket的for/product
循环很方便:
(for/product ([n (in-range 1 ...some-large-number...)])
(p_cos_aux x n))
让我们尝试为大数字输入100:
(define (p_cos x)
(for/product ([n (in-range 1 100)])
(p_cos_aux x n)))
尝试一下:
> (p_cos 0)
1
> (p_cos (* 1/4 pi))
0.707553324600212
> (p_cos (* 1/2 pi))
0.0
> (p_cos (* 3/4 pi))
-0.7111358730792002
> (p_cos pi)
-1.01015228426396
> (p_cos (* 5/4 pi))
-0.7183556654338034
> (p_cos (* 3/2 pi))
-0.0
> (p_cos (* 7/4 pi))
0.7293234913165205
> (p_cos (* 2 pi))
1.0412338930105425
它并不完美,但你可以通过将100
增加到更大的数字来获得更好的近似值。