传送门 : zoj 2671
summary
下次, 线段树不用cin, cout了有毒啊
AC code:
#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
const int maxn = 30000 + 5;
int R, n, M, q;
struct Matrix {
int v[2][2];
void clr() {
memset(v, 0, sizeof(v));
}
void E() {
clr();
for (int i = 0; i < 2; ++i) v[i][i] = 1;
}
void init(int a, int b, int c, int d) {
v[0][0] = a;
v[0][1] = b;
v[1][0] = c;
v[1][1] = d;
}
void debug() {
for (int i = 0; i < 2; ++i)
for (int j = 0; j < 2; ++j)
printf("%d%s", v[i][j], (j == 1 ? "\n" : " "));
}
Matrix operator * (Matrix b) {
Matrix res;
res.clr();
for (int i = 0; i < 2; ++i)
for (int j = 0; j < 2; ++j)
for (int k = 0; k < 2; ++k)
res.v[i][j] = (res.v[i][j] + v[i][k] * b.v[k][j]) % R;
return res;
}
//Matrix
}a[maxn << 2];
void build() {//zkw线段树
int x1, y1, x2, y2;;
for (M = 1; M <= n + 1; M <<= 1);
for (int i = M + 1; i <= M + n; ++i) {
scanf("%d%d%d%d", &x1, &y1, &x2, &y2);
a[i].init(x1, y1, x2, y2);
}
for (int i = M - 1; i; --i) {
a[i] = a[i << 1] * a[i << 1 | 1];
}
}
Matrix query(int l, int r) {
l += M - 1;
r += M + 1;
Matrix tmp, la, ra;
la.E();
ra.E();
while (r ^ l ^ 1) {
if (~l & 1) la = la * a[l + 1];//方向问题, 后来才反应过来
if (r & 1) ra = a[r - 1] * ra;
l >>= 1;
r >>= 1;
}
tmp = la * ra;
return tmp;
}
int main() {
#ifndef ONLINE_JUDGE
freopen("in.txt", "r", stdin);
#endif
cin.tie(0);
cin.sync_with_stdio(false);
int l, r, cas = 0;
while (~scanf("%d%d%d", &R, &n, &q)) {
for (int i = 1; i < maxn << 2; ++i) a[i].E();
build();
if (cas++) puts("");
while (q--) {
scanf("%d%d", &l, &r);
Matrix ans = query(l, r);
ans.debug();
if (q) puts("");
}
}
return 0;
}