详解Python牛顿插值法


Posted in Python onMay 11, 2021

一、牛顿多项式

拉格朗日多项式的公式不具备递推性,每个多项式需要单独构造。但很多时候我们需要从若干个逼近多项式选择一个。这个时候我们就需要一个具有递推关系的方法来构造——牛顿多项式

详解Python牛顿插值法

这里的的a0,a1…等可以通过逐一带入点的值来求得。但是当项数多起来时,会发现式子变得很大,这个时候我们便要引入差商的概念(利用差分思想)具体见式子能更好理解

详解Python牛顿插值法
详解Python牛顿插值法

这里在编程实现中我们可以推出相应的差商推导方程

d(k,0)=y(k)
d(k,j)=(d(k,j-1)-d(k-1,j-1)) / (x(k)-x(k-j))

二、例题

【问题描述】考虑[0,3]内的函数y=f(x)=cos(x)。利用多个(最多为6个)节点构造牛顿插值多项式。
【输入形式】在屏幕上依次输入在区间[0,3]内的一个值x*,构造插值多项式后求其P(x*)值,和多个节点的x坐标。
【输出形式】输出牛顿插值多项式系数向量,差商矩阵,P(x*)值(保留6位有效数字),和与真实值的绝对误差(使用科学计数法,保留小数点后6位有数字)。
【样例1输入】
0.8
0 0.5 1
【样例1输出】
-0.429726
-0.0299721
1
1 0 0
0.877583 -0.244835 0
0.540302 -0.674561 -0.429726
0.700998
4.291237e-03
【样例1说明】
输入:x为0.8,3个节点为(k, cos(k)),其中k = 0, 0.5, 1。
输出:
牛顿插值多项式系数向量,表示P2(x)=-0.429726x^2 - 0.0299721x + 1;
3行3列的差商矩阵;
当x
为0.8时,P2(0.8)值为0.700998
与真实值的绝对误差为:4.291237*10^(-3)
【评分标准】根据输入得到的输出准确

三、ACcode:

C++(后面还有python代码)

/*
 * @Author: csc
 * @Date: 2021-04-30 08:52:45
 * @LastEditTime: 2021-04-30 11:57:46
 * @LastEditors: Please set LastEditors
 * @Description: In User Settings Edit
 * @FilePath: \code_formal\course\cal\newton_quo.cpp
 */
#include <bits/stdc++.h>
#define pr printf
#define sc scanf
#define for0(i, n) for (i = 0; i < n; i++)
#define for1n(i, n) for (i = 1; i <= n; i++)
#define forab(i, a, b) for (i = a; i <= b; i++)
#define forba(i, a, b) for (i = b; i >= a; i--)
#define pb push_back
#define eb emplace_back
#define fi first
#define se second
#define int long long
#define pii pair<int, int>
#define vi vector<int>
#define vii vector<vector<int>>
#define vt3 vector<tuple<int, int, int>>
#define mem(ara, n) memset(ara, n, sizeof(ara))
#define memb(ara) memset(ara, false, sizeof(ara))
#define all(x) (x).begin(), (x).end()
#define sq(x) ((x) * (x))
#define sz(x) x.size()
const int N = 2e5 + 100;
const int mod = 1e9 + 7;
namespace often
{
    inline void input(int &res)
    {
        char c = getchar();
        res = 0;
        int f = 1;
        while (!isdigit(c))
        {
            f ^= c == '-';
            c = getchar();
        }
        while (isdigit(c))
        {
            res = (res << 3) + (res << 1) + (c ^ 48);
            c = getchar();
        }
        res = f ? res : -res;
    }
    inline int qpow(int a, int b)
    {
        int ans = 1, base = a;
        while (b)
        {
            if (b & 1)
                ans = (ans * base % mod + mod) % mod;
            base = (base * base % mod + mod) % mod;
            b >>= 1;
        }
        return ans;
    }
    int fact(int n)
    {
        int res = 1;
        for (int i = 1; i <= n; i++)
            res = res * 1ll * i % mod;
        return res;
    }
    int C(int n, int k)
    {
        return fact(n) * 1ll * qpow(fact(k), mod - 2) % mod * 1ll * qpow(fact(n - k), mod - 2) % mod;
    }
    int exgcd(int a, int b, int &x, int &y)
    {
        if (b == 0)
        {
            x = 1, y = 0;
            return a;
        }
        int res = exgcd(b, a % b, x, y);
        int t = y;
        y = x - (a / b) * y;
        x = t;
        return res;
    }
    int invmod(int a, int mod)
    {
        int x, y;
        exgcd(a, mod, x, y);
        x %= mod;
        if (x < 0)
            x += mod;
        return x;
    }
}
using namespace often;
using namespace std;

int n;

signed main()
{
    auto polymul = [&](vector<double> &v, double er) {
        v.emplace_back(0);
        vector<double> _ = v;
        int m = sz(v);
        for (int i = 1; i < m; i++)
            v[i] += er * _[i - 1];
    };
    auto polyval = [&](vector<double> const &c, double const &_x) -> double {
        double res = 0.0;
        int m = sz(c);
        for (int ii = 0; ii < m; ii++)
            res += c[ii] * pow(_x, (double)(m - ii - 1));
        return res;
    };

    int __ = 1;
    //input(_);
    while (__--)
    {
        double _x, temp;
        cin >> _x;
        vector<double> x, y;
        while (cin >> temp)
            x.emplace_back(temp), y.emplace_back(cos(temp));
        n = x.size();
        vector<vector<double>> a(n, vector<double>(n));
        int i, j;
        for0(i, n) a[i][0] = y[i];
        forab(j, 1, n - 1) forab(i, j, n - 1) a[i][j] = (a[i][j - 1] - a[i - 1][j - 1]) / (x[i] - x[i - j]);
        vector<double> v;
        v.emplace_back(a[n - 1][n - 1]);
        forba(i, 0, n - 2)
        {
            polymul(v, -x[i]);
            int l = sz(v);
            v[l - 1] += a[i][i];
        }

        for0(i, n)
            pr("%g\n", v[i]);
        for0(i, n)
        {
            for0(j, n)
                pr("%g ", a[i][j]);
            puts("");
        }
        double _y =  polyval(v, _x);
        pr("%g\n", _y);
        pr("%.6e",fabs(_y-cos(_x)));
    }

    return 0;
}

python代码

'''
Author: csc
Date: 2021-04-29 23:00:57
LastEditTime: 2021-04-30 09:58:07
LastEditors: Please set LastEditors
Description: In User Settings Edit
FilePath: \code_py\newton_.py
'''
import numpy as np


def difference_quotient(x, y):
    n = len(x)
    a = np.zeros([n, n], dtype=float)
    for i in range(n):
        a[i][0] = y[i]
    for j in range(1, n):
        for i in range(j, n):
            a[i][j] = (a[i][j-1]-a[i-1][j-1])/(x[i]-x[i-j])
    return a


def newton(x, y, _x):
    a = difference_quotient(x, y)
    n = len(x)
    s = a[n-1][n-1]
    j = n-2
    while j >= 0:
        s = np.polyadd(np.polymul(s, np.poly1d(
            [x[j]], True)), np.poly1d([a[j][j]]))
        j -= 1
    for i in range(n):
        print('%g' % s[n-1-i])
    for i in range(n):
        for j in range(n):
            print('%g' % a[i][j], end=' ')
        print()
    _y = np.polyval(s, _x)
    print('%g' % _y)
    # re_err
    real_y = np.cos(_x)
    err = abs(_y-real_y)
    print('%.6e' % err)


def main():
    _x = float(input())
    x = list(map(float, input().split()))
    y = np.cos(x)
    newton(x, y, _x)


if __name__ == '__main__':
    main()

到此这篇关于详解Python牛顿插值法的文章就介绍到这了,更多相关Python牛顿插值法内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Python 相关文章推荐
Django框架中方法的访问和查找
Jul 15 Python
学生信息管理系统python版
Oct 17 Python
python实现点击按钮修改数据的方法
Jul 17 Python
Python坐标线性插值应用实现
Nov 13 Python
pycharm双击无响应(打不开问题解决办法)
Jan 10 Python
如何基于Python实现数字类型转换
Feb 07 Python
python安装和pycharm环境搭建设置方法
May 27 Python
Django实现微信小程序支付的示例代码
Sep 03 Python
Django用内置方法实现简单搜索功能的方法
Dec 18 Python
Python requests库参数提交的注意事项总结
Mar 29 Python
Python字典的基础操作
Nov 01 Python
详解pytorch创建tensor函数
Mar 22 Python
Python中使用subprocess库创建附加进程
有趣的二维码:使用MyQR和qrcode来制作二维码
python保存大型 .mat 数据文件报错超出 IO 限制的操作
May 10 #Python
Python批量将csv文件转化成xml文件的实例
python基础之爬虫入门
python设置 matplotlib 正确显示中文的四种方式
提取视频中的音频 Python只需要三行代码!
You might like
php 特殊字符处理函数
2008/09/05 PHP
php学习之 认清变量的作用范围
2010/01/26 PHP
php语言流程控制中的主动与被动
2012/11/05 PHP
PHP中基本HTTP认证技巧分析
2015/03/16 PHP
获取HTML DOM节点元素的方法的总结
2009/08/21 Javascript
Javascript将string类型转换int类型
2010/12/09 Javascript
用jQuery模拟页面加载进度条的实现代码
2011/12/19 Javascript
JQuery 返回布尔值Is()条件判断方法代码
2012/05/14 Javascript
js中scrollTop()方法和scroll()方法用法示例
2016/10/03 Javascript
JavaScript中数组的各种操作的总结(必看篇)
2017/02/13 Javascript
Webpack+Vue如何导入Jquery和Jquery的第三方插件
2017/02/20 Javascript
vue实现通讯录功能
2018/07/14 Javascript
Angular中sweetalert弹框的基本使用教程
2018/07/22 Javascript
详解vue.js下引入百度地图jsApi的两种方法
2018/07/27 Javascript
js异步上传多张图片插件的使用方法
2018/10/22 Javascript
微信小程序bindinput与bindsubmit的区别实例分析
2019/04/17 Javascript
js继承的这6种方式!(上)
2019/04/23 Javascript
浅析Vue 中的 render 函数
2020/02/28 Javascript
JS Html转义和反转义(html编码和解码)的实现与使用方法总结
2020/03/10 Javascript
Python在不同目录下导入模块的实现方法
2017/10/27 Python
解决matplotlib库show()方法不显示图片的问题
2018/05/24 Python
python使用Matplotlib改变坐标轴的默认位置
2019/10/18 Python
Python中zip函数如何使用
2020/06/04 Python
基于Python爬虫采集天气网实时信息
2020/06/05 Python
如何使用canvas绘制可移动网格的示例代码
2020/12/14 HTML / CSS
维多利亚的秘密官方网站:Victoria’s Secret
2018/10/24 全球购物
个人自荐信
2013/12/05 职场文书
中学家长会邀请函
2014/01/17 职场文书
2014年应届大学生毕业自我鉴定
2014/01/31 职场文书
教师节演讲稿
2014/05/06 职场文书
美国留学经济担保书
2014/05/20 职场文书
2014办公室年度工作总结
2014/12/09 职场文书
主持人大赛开场白
2015/05/29 职场文书
中学生国庆节演讲稿2015
2015/07/30 职场文书
安全教育日主题班会
2015/08/13 职场文书
css实现文章分割线样式的多种方法总结
2021/04/21 HTML / CSS