BZOJ 4569 萌萌哒

题目传送门

4569: [Scoi2016]萌萌哒

Time Limit: 10 Sec Memory Limit: 256 MB

Submit: 483 Solved: 221

[Submit][Status][Discuss]

## **Description** 一个长度为n的大数,用S1S2S3...Sn表示,其中Si表示数的第i位,S1是数的最高位,告诉你一些限制条件,每个条 件表示为四个数,l1,r1,l2,r2,即两个长度相同的区间,表示子串Sl1Sl1+1Sl1+2...Sr1与Sl2Sl2+1Sl2+2...S r2完全相同。比如n=6时,某限制条件l1=1,r1=3,l2=4,r2=6,那么123123,351351均满足条件,但是12012,13 1141不满足条件,前者数的长度不为6,后者第二位与第五位不同。问满足以上所有条件的数有多少个。 ## **Input** 第一行两个数n和m,分别表示大数的长度,以及限制条件的个数。接下来m行,对于第i行,有4个数li1,ri1,li2 ,ri2,分别表示该限制条件对应的两个区间。 1≤n≤10^5,1≤m≤10^5,1≤li1,ri1,li2,ri2≤n;并且保证ri1-li1=ri2-li2。 ## **Output** 一个数,表示满足所有条件且长度为n的大数的个数,答案可能很大,因此输出答案模10^9+7的结果即可。 ## **Sample Input** 4 2 1 2 3 4 3 3 3 3 ## **Sample Output** 90 ## **题解** 这道题显然要用并查集,不过需要进行区间合并。所以我最开始选择了线段树···· 在经历千辛万苦之后,我确定了线段树并不能搞定此题。 看此题数据,我们就蒙一个$O(n\log (n))$级的算法。这样我们可以用f[i][j]来表示一段区间的父亲。 最暴力的方法就是表示i..j区间的父亲,但显然会炸。我们就联想到倍增,用f[i][j]表示i..i+(2^j)-1的区间父亲。 这样我们对于每一个区间的合并,我们最多进行$\log n$次合并,在算上并查集的$O(\alpha (a))$ ,总的复杂度为$O(n\log n \alpha (a))$ 。 ``` c++ #include //Input char Inc; int Ina; inline int geti() { while ((Inc = getchar()) < '0' || Inc > '9'); Ina = Inc - '0'; while ((Inc = getchar()) >= '0' && Inc <= '9') Ina = (Ina << 3) + (Ina << 1) + Inc - '0'; return Ina; } // const int Mod = 1e9 + 7, N = 100005; int f[N][17]; bool vis[N]; int find(int i, int j) { return (f[i][j] ^ i) ? f[i][j] = find(f[i][j], j) : i; }

void Union(int k, int i, int j) {
if (find(i, k) ^ find(j, k)) {
f[f[i][k]][k] = f[j][k];
if (!k--) return;
Union(k, i, j); Union(k, i + (1 << k), j + (1 << k));
}
}

int main() {
int n, m, i, j, a, b, c, d, ans;
n = geti(), m = geti();
if (n < 2) return puts("9"), 0;
for (j = 0; (1 << j) <= n; ++j)
for (i = 1; i + (1 << j) - 1 <= n; ++i)
f[i][j] = i;
while (m--) {
a = geti(), b = geti(), c = geti(), d = geti();
j = b - a + 1, i = 0;
while ((1 << i + 1) <= j) ++i;
Union(i, a, c); Union(i, b - (1 << i) + 1, d - (1 << i) + 1);
}
ans = 9; vis[find(1, 0)] = true;
for (i = 2; i <= n; ++i) if (!vis[find(i, 0)]) vis[find(i, 0)] = true, ans = 10LL * ans % Mod;
printf("%d\n", ans);
return 0;
}

posted @ 2016-09-04 11:27  cycleke  阅读(218)  评论(0编辑  收藏  举报