1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101
|
#include <iostream> #include <cstdio> #include <algorithm> #include <cstring> #include <cmath> #include <queue> #include <set> #include <vector> using namespace std;
const int INF = ~0u>>1; typedef pair <int,int> P; #define MID(x,y) ((x+y)>>1) #define iabs(x) ((x)>0?(x):-(x)) #define REP(i,a,b) for(int i=(a);i<(b);i++) #define FOR(i,a,b) for(int i=(a);i<=(b);i++) #define pb push_back #define mp make_pair #define print() cout<<"--------"<<endl #define lson l, m , rt << 1 #define rson m + 1, r , rt << 1 | 1
#define maxn 400040 typedef long long ll; #define mod 1000000007 struct mat{ ll a[2][2]; mat(){ memset(a,0,sizeof(a)); } mat(ll x){ a[0][0] = a[1][0] = 1; a[1][1] = 0; a[0][1] = x; } mat operator * (const mat &b) const{ mat ret = mat(); for (int i = 0; i < 2; i ++){ for (int j = 0; j < 2; j ++){ for (int k = 0; k < 2; k ++){ ret.a[i][j] = (ret.a[i][j] + a[i][k] * b.a[k][j]) % mod; } } } return ret; } };
ll num[maxn]; mat sum[maxn];
void PushUp(int rt){ sum[rt] = sum[rt << 1 | 1] * sum[rt << 1]; }
void build(int l, int r, int rt){ if (l == r) { sum[rt] = mat(num[l]); return; } int m = MID(l,r); build(lson); build(rson); PushUp(rt); }
mat query(int L,int R, int l, int r, int rt){ if (L <= l && r <= R) return sum[rt]; int m = MID(l, r); if (R <= m) return query(L, R, lson); if (L > m) return query(L, R, rson); return query(L,R,rson) * query(L,R,lson); }
int main(){ int T,n,m; cin >> T; mat t; while (T--){ scanf("%d%d", &n, &m); for (int i = 1; i <= n; i ++){ scanf("%lld", &num[i]); } build(1, n, 1); int l,r; for (int i = 0; i < m; i ++){ scanf("%d%d", &l, &r); if (l == r || r == l + 1){ printf("%lldn", num[r]);continue; } t = query(l + 2,r,1,n,1); printf("%lldn", (t.a[0][0] * num[l + 1] + t.a[0][1] * num[l]) % mod); } } return 0; }
|