【问题标题】:Evaluating sinx using Horner's rule with recursion使用带递归的霍纳规则评估 sinx
【发布时间】:2020-12-12 19:16:34
【问题描述】:

由于我最近学习了Horner's rule。我决定在 taylor series 的帮助下使用相同的方法评估 sinx。我写了一些代码,但它与原始结果有很大的偏差。

#include<iostream>
using namespace std;

double sin(double x, int n)
{
    static double s = x;
    if(n==1)
    {
        return s;
    }
    else
    {
        s *= 1-((x*x)/((2*n-1)*(2*n-2)));
    }
    return sin(x,n-1);
}

int main()
{
    double r = sin(1,15);
    cout << r;
    return 0;
}

其中 n 是泰勒级数的项数

所以,按照上面提到的参数传递,预期的结果应该是0.841,但是当我的程序计算时,它显示的是0.735。我也尝试将 n 作为一个非常大的数字,但它显示出比以前更大的偏差。任何帮助将不胜感激。提前谢谢你!

【问题讨论】:

  • 我不确定公式,但你编写函数的方式只能在你第一次调用它时工作。因为s 仅初始化一次(在第一次调用时)。此后的所有其他调用都会给出错误的结果,即使公式是正确的。
  • 将共享可变状态(如静态变量)与递归混合通常不是一个好主意。
  • 这里不需要递归,使用循环将消除对静态变量的需要
  • 你确定你的“霍纳变换”是正确的吗?
  • @VaibhavSharma Here 是没有递归的相同算法(如果我没看错的话)。它有相同的错误,但更容易阅读。

标签: c++ recursion trigonometry taylor-series


【解决方案1】:

根据@Ted Lyngmo 的评论,here 是一个工作版本,稍作修改。

在您的原始代码中,您可以执行this:

#include<iostream>
#include <cmath>

using namespace std;

double sin(double x, int n, double s = 1)
{
    if(n==1)
    {
        return s*x;
    }
    else
    {
        s = 1 - s*((x*x)/((2*n-1)*(2*n-2)));
    }
    return sin(x, n-1, s);
}

int main()
{
    cout << "std::sin(0.5) = " << std::sin(0.5) << std::endl; 
    double r = sin(0.5, 15);
    cout << r;
    return 0;
}

我还建议您使用 x != 1 检查您的公式,因为这样更难错过乘法 x 因子。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-04-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-07-12
    • 1970-01-01
    • 1970-01-01
    • 2019-09-07
    相关资源
    最近更新 更多