IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 数据结构与算法 -> 【模板】智乃酱的静态数组维护问题多项式(多次差分数组——多项式处理) -> 正文阅读

[数据结构与算法]【模板】智乃酱的静态数组维护问题多项式(多次差分数组——多项式处理)

题目

原题链接


问题描述

在这里插入图片描述


思路

差分数组的优点在于牵一发而动全身,通过处理一个位置便可以将后续位置的值都改变。

我们此时面临的操作是对区间处理,而且处理不是简单的加上某个值,而是对位于 [ l , r ] [l,r] [l,r]中的 a [ i ] a[i] a[i]加上 f ( i ) f(i) f(i) f ( i ) f(i) f(i)是一个最高阶数不超过 5 5 5的多项式。

1.引入

在题目小W的糖果中,需要处理平方差分数组,也就是对于位置 l l l以及其右侧的每个位置需要加上 i 2 i^2 i2,其实这也是一个特殊的多项式,我们通过进行 3 3 3次差分:
[ 1 , 4 , 9 , 16 , 25 ] ? [ 1 , 3 , 5 , 7 , 9 ] ? [ 1 , 2 , 2 , 2 , 2 ] ? [ 1 , 1 , 0 , 0 , 0 ] [1,4,9,16,25]\Longrightarrow[1,3,5,7,9]\Longrightarrow[1,2,2,2,2]\Longrightarrow[1,1,0,0,0] [1,4,9,16,25]?[1,3,5,7,9]?[1,2,2,2,2]?[1,1,0,0,0]

在数学上,有一个结论:最高次项为 n n n次的 n n n阶多项式做 n + 1 n+1 n+1阶差分后余项为常数(非0项有限)。

依照这个定理,我们对一个序列上特定的位置加上特定的常数,再经过 n + 1 n+1 n+1次前缀和操作,就可以对位于 [ l , + ∞ ) [l,+\infty) [l,+)中的 a [ i ] a[i] a[i]加上最高次项为 n n n次的 n n n阶多项式 f ( i ) f(i) f(i)

值得注意的是,如果我们对最高次项为 n n n次的 n n n阶多项式做 n + 2 n+2 n+2阶差分,我们会得到什么样的结果呢?
依然使用上面的例子,再进行一次差分,我们将会得到序列 [ 1 , 0 , ? 1 , 0 , 0 ] [1,0,-1,0,0] [1,0,?1,0,0],这个序列依然是一个非 0 0 0项有限的序列。

此时又有了另一个问题,也就是这个非 0 0 0项有限的序列的长度可能会在什么范围内,我们取 f ( x ) = x 5 + x 4 + x 3 + x 2 + x + 6 f(x)=x^5+x^4+x^3+x^2+x+6 f(x)=x5+x4+x3+x2+x+6来看看
在这里插入图片描述
6 6 6次差分后也就 6 6 6项,所以我们一开始设定 10 10 10位就可以推出这个序列了。

2.分析

但上述题目中的操作并不是对右侧全部元素进行操作,而是对区间 [ l , r ] [l,r] [l,r]内部元素进行操作,所以我们需要对 [ r + 1 , + ∞ ) [r+1,+\infty) [r+1,+)中的每个元素进行修正,此时也就是对这一段的每个元素加上 ? f ( i ) -f(i) ?f(i),依然可以将 ? f ( i ) -f(i) ?f(i)视作是一个多项式,经过多次差分得到一个非 0 0 0项有限的序列。

代码

#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int mod =1e9+7;
const int N =1e5+7;
#define fir(i, a, b) for (int i = (a); i <= (b); i++)
#define rif(i, a, b) for (int i = (a); i >= (b); i--)
ll t,n,m,q,a[N],l,r,k,c[15],p[2][15];
ll f(ll x, ll a[],ll k){
	ll res = 0;
	ll base = 1;
	fir(i,0,k){
		(res+=base*c[i])%=mod;
		(base*=x)%=mod;
	}
	return res;
}
ll g(ll x,ll a[],ll k,ll l,ll r){
	return (mod-f(x+r-l+1,a,k))%mod;
}
void P(ll a[], int len, int cnt){
	while(cnt--){
		fir(i,1,len){
			(a[i]+=a[i-1])%=mod;
		}
	}
}
void D(ll a[], int len, int cnt){
	while(cnt--){
		rif(i,len,0){
			a[i]=(a[i]-a[i-1]+mod)%mod;
		}
	}
}
int main(){
	scanf("%lld %lld %lld", &n, &m, &q);
	fir(i,1,n)scanf("%lld", &a[i]);
	D(a,n,6);
	while(m--){
		cin>>l>>r>>k;
		rif(i,k,0)scanf("%lld", &c[i]);
		fir(i,1,10){
			p[0][i]=f(i,c,k);
			p[1][i]=g(i,c,k,l,r);
		}
		D(p[0],10,6);
		D(p[1],10,6);
		fir(i,1,10){
			(a[l+i-1]+=p[0][i])%=mod;
			(a[r+i]+=p[1][i])%=mod;
		}
	}
	P(a,n,7);
	while(q--){
		scanf("%lld %lld", &l, &r);
		printf("%lld\n",((a[r]-a[l-1])%mod+mod)%mod);
	}
}
  数据结构与算法 最新文章
【力扣106】 从中序与后续遍历序列构造二叉
leetcode 322 零钱兑换
哈希的应用:海量数据处理
动态规划|最短Hamilton路径
华为机试_HJ41 称砝码【中等】【menset】【
【C与数据结构】——寒假提高每日练习Day1
基础算法——堆排序
2023王道数据结构线性表--单链表课后习题部
LeetCode 之 反转链表的一部分
【题解】lintcode必刷50题<有效的括号序列
上一篇文章      下一篇文章      查看所有文章
加:2022-02-26 11:55:08  更:2022-02-26 11:56:04 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/26 16:58:39-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码