Calculate the Function

Time Limit:2000MS     Memory Limit:65536KB     64bit IO Format:%lld & %llu

Submit Status
Appoint description: 
System Crawler  (2014-04-09)

Description

You are given a list of numbers A1A2 .. AN and M queries. For the i-th query:

  • The query has two parameters Li and Ri.
  • The query will define a function Fi(x) on the domain [Li, Ri] ∈ Z.
  • Fi(Li) = ALi
  • Fi(Li + 1) = A(Li + 1)
  • for all x >= Li + 2Fi(x) = Fi(x - 1) + Fi(x - 2) × Ax

You task is to calculate Fi(Ri) for each query. Because the answer can be very large, you should output the remainder of the answer divided by 1000000007.

Input

There are multiple test cases. The first line of input is an integer T indicates the number of test cases. For each test case:

The first line contains two integers NM (1 <= NM <= 100000). The second line contains N integers A1A2 .. AN (1 <= Ai <= 1000000000).

The next M lines, each line is a query with two integer parameters LiRi (1 <= Li <= Ri <= N).

Output

For each test case, output the remainder of the answer divided by 1000000007.

Sample Input

1
4 7
1 2 3 4
1 1
1 2
1 3
1 4
2 4
3 4
4 4

Sample Output

1
2
5
13
11
4
4

题目大意:给一个n的序列,若干查询(L,R)。输出F(R)的值。

函数关系:

        F(L)=A(L)

        F(L+1)=A(L+1)

        F(X)=F(X-1)+F(X-2)*A(X) (X-L>=2)

因此每段(L,R)区间               

| F(R) |   | 1 A(R)|*| 1  A(R-1)| *......* | 1  A(L+2)|*| A(L+1)|

|F(R-1)| = | 1   0 | | 1    0   |  ......  | 1    0   | | A(L)  |

每次查询(L+2,R)区间的矩阵乘积再稍微处理一下就行了(当R-L>1时)。

 #include<iostream>
#include<cstdio>
#include<cstring>
using namespace std; #define Mod 1000000007
typedef long long LL;
const int maxn=;
LL a[maxn]; struct node
{
LL mat[][];
void set(int x)//初始化矩阵
{
mat[][]=;
mat[][]=a[x]%Mod;
mat[][]=;
mat[][]=; }
}; struct IntervalTree
{
int left,right;
node matrix;
}f[maxn<<]; node mat_mul_mod(node A,node B)//矩阵乘法取模
{
node ret;
ret.mat[][]=(A.mat[][]*B.mat[][]%Mod+A.mat[][]*B.mat[][]%Mod)%Mod;
ret.mat[][]=(A.mat[][]*B.mat[][]%Mod+A.mat[][]*B.mat[][]%Mod)%Mod;
ret.mat[][]=(A.mat[][]*B.mat[][]%Mod+A.mat[][]*B.mat[][]%Mod)%Mod;
ret.mat[][]=(A.mat[][]*B.mat[][]%Mod+A.mat[][]*B.mat[][]%Mod)%Mod;
return ret;
} void bulid(int left,int right,int i)//建树
{
int mid;
f[i].left=left;
f[i].right=right;
if(left==right)
{
f[i].matrix.set(left);
return;
}
mid=(left+right)>>;
bulid(left,mid,i<<);
bulid(mid+,right,i<<|);
f[i].matrix=mat_mul_mod(f[i<<|].matrix,f[i<<].matrix);
return ;
} node query(int left,int right,int i)//查询
{
int mid;
if(f[i].left==left && f[i].right==right) return f[i].matrix;
mid=(f[i].left+f[i].right)>>;
if(right<=mid) return query(left,right,i<<);
else if(left>mid) return query(left,right,i<<|);
else return mat_mul_mod(query(mid+,right,i<<|),query(left,mid,i<<));
} int main()
{
int t,n,m,i,lp,rp;
scanf("%d",&t);
while(t--)
{
scanf("%d %d",&n,&m);
for(i=;i<=n;i++)
scanf("%lld",&a[i]);
bulid(,n,);
while(m--)
{
scanf("%d %d",&lp,&rp);
if(lp==rp || lp+==rp)
{
printf("%lld\n",a[rp]%Mod);
continue;
}
node temp=query(lp+,rp,);
printf("%lld\n",(temp.mat[][]*a[lp+]%Mod+temp.mat[][]*a[lp]%Mod)%Mod);
}
}
return ;
}

ZOJ 3772 Calculate the Function 线段树+矩阵的更多相关文章

  1. Z0J 3772 Calculate the Function 线段树+矩阵

    http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemId=5235 这种题目居然没想到,一开始往矩阵快速幂想去了,因为之前跪了太多矩阵快速幂 ...

  2. ZOJ3772 - Calculate the Function(线段树+矩阵)

    题目大意 给定一个序列A1 A2 .. AN 和M个查询 每个查询含有两个数 Li 和Ri. 查询定义了一个函数 Fi(x) 在区间 [Li, Ri] ∈ Z. Fi(Li) = ALi Fi(Li ...

  3. 线段树 + 矩阵 --- ZOJ 3772 Calculate the Function

    Calculate the Function Problem's Link:   http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCod ...

  4. zoj 3772 Calculate the Function

    http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemId=5235 这道题需要构造矩阵:F(X)=F(X-1)+F(X-2)*A(X)转化为 ...

  5. Wannafly Winter Camp 2019.Day 8 div1 E.Souls-like Game(线段树 矩阵快速幂)

    题目链接 \(998244353\)写成\(99824435\)然后调这个线段树模板1.5h= = 以后要注意常量啊啊啊 \(Description\) 每个位置有一个\(3\times3\)的矩阵, ...

  6. Codeforces Round #337 (Div. 2) D. Vika and Segments 线段树 矩阵面积并

    D. Vika and Segments     Vika has an infinite sheet of squared paper. Initially all squares are whit ...

  7. CF719E(线段树+矩阵快速幂)

    题意:给你一个数列a,a[i]表示斐波那契数列的下标为a[i],求区间对应斐波那契数列数字的和,还要求能够维护对区间内所有下标加d的操作 分析:线段树 线段树的每个节点表示(f[i],f[i-1])这 ...

  8. 【Codeforces718C】Sasha and Array 线段树 + 矩阵乘法

    C. Sasha and Array time limit per test:5 seconds memory limit per test:256 megabytes input:standard ...

  9. LOJ2980 THUSC2017大魔法师(线段树+矩阵乘法)

    线段树每个节点维护(A,B,C,len)向量,操作即是将其乘上一个矩阵. #include<iostream> #include<cstdio> #include<cma ...

随机推荐

  1. Vue中npm run build报“Error in parsing SVG: Unquoted attribute value”

    自己做的一个Vue项目,在打包时老是报这个错误 # Error in parsing SVG: Unquoted attribute value 查了查网上说的,都说报错原因是压缩和抽离CSS的插件中 ...

  2. JQuery EasyUI学习记录(二)

    1.jquery easyUI动态添加选项卡(查看jquery easyUI手册) 1.1 用于动态添加一个选项卡 1.1.1 选中指定的选项卡和判断某个选项卡是否存在 测试代码: <a id= ...

  3. Mybatis学习记录(3)

    1.输出映射和输入映射 Mapper.xml映射文件定义了操作数据库的sql,每个sql就是一个statement,映射文件是mybatis的核心. (1)parameterType(输入类型)   ...

  4. Java基础面试操作题: 线程问题,写一个死锁(原理:只有互相都等待对方放弃资源才会产生死锁)

    package com.swift; public class DeadLock implements Runnable { private boolean flag; DeadLock(boolea ...

  5. 记住密码功能 JS结合JQuery 操作 Cookie 实现记住密码和用户名!

    // 记住密码功能 JS结合JQuery 操作 Cookie 实现记住密码和用户名! var username = document.getElementById("username&quo ...

  6. 洛谷 P2127 序列排序

    https://www.luogu.org/problemnew/show/P2127 感觉题解里写的比较复杂,可能自己的想法比较简单一点吧. 看这个图中的的点如果形成一个环,贪心的考虑,要想花费最少 ...

  7. 洛谷 P2717 寒假作业

    https://www.luogu.org/problemnew/show/P2717 $n \le 1004枚举区间,挨个计算,判断,时间复杂度$O(n^3)$. $n \le 5000$,预处理出 ...

  8. 转 救命的教程 anaconda下载安装包网络错误的解决办法

    折腾了一天,终于找到了这个解决办法 https://blog.csdn.net/sinat_29315697/article/details/80516498

  9. PHP做ERP, CRM, CMS系统需要注意哪些地方

    php作为二次开发弱类型语言, 可读性, 可视度都是比较高的. 在很多人眼里, 也许php只能做一些web应用开发, 比如某个公司的网站, 某个公司的网站后台, 其实,我可以告诉大家, php不比任何 ...

  10. Python学习笔记:time模块和datetime模块(时间和日期)

    time模块 time模块通常用来操作时间戳信息(各种“秒”),常用的方法有: time.sleep(seconds):将当前程序阻塞指定秒数,然后继续运行程序. time.time():返回当前时间 ...