codeforces-div1-286-D
2015-01-19 16:31
351 查看
题目链接 Mr. Kitayuta's Colorful Graph
直接讲解法, 主要方法是分情况来做.
怎么分情况呢?
首先对于每个颜色分别处理, 处理的时候就直接用并查集, 把这种颜色能够连接起来的边搞到一个集合里面.
然后用这个颜色的并查集结果来离线更新答案, 更新的时候, 分两种情况,
1. 这个颜色的边个数大于 lim
2. 这个颜色的边小于等于 lim
PS. lim的取值会影响效率, 具体分析见下面
1. 这种情况下, 我们令ans[k]为当前第k个询问的答案, 更新答案的时候就直接遍历每个询问, 如果询问的两个节点在一个并查集内, 则这个询问的答案 + 1, 也就是ans[k] ++;
2. 这种情况下要稍微复杂一点点.
我们需要一个辅助的map <pair<int, int>, int> M;
初始化的时候遍历 每个询问 q[i][2], 令M[ make_pair(q[i][0], q[i][1]) ] = M[ make_pair(q[i][1], q[i][0]) ] = 0;
然后我们准备把这种情况下的答案保存在M中.
具体的方法是遍历这个颜色的所有边, 取出这些边相连的所有节点放到一个集合S里.
现在再遍历S中的每个节点对(a, b), 如果M.count((a, b)) == 1, 那么 M[(a, b)] ++, M[(b, a)] ++;
最后对于每个询问k, 假设他询问的是节点a和b, 那么其答案就是, ans[k] + M[(a, b)]
效率分析
1. 这种情况下, 每次更新的复杂度是 O(Q), 其中Q是询问的个数
2. 这种情况下, 每次更新的复杂度是 O(lim*lim*log(Q)); lim*lim即是点对的个数, log(Q)是更新M的复杂度.
于是总复杂度就是 Q*A1 + lim*lim*log(Q)*A2, 其中 A1, A2分别为情况1和情况2的个数.
根据分类的定义, 可知A1 <= M / lim.
于是我们可以估计lim的值来计算各种情况下的总效率.
最后可以发现当lim在30左右的时候, 效果不错.
下面是代码
直接讲解法, 主要方法是分情况来做.
怎么分情况呢?
首先对于每个颜色分别处理, 处理的时候就直接用并查集, 把这种颜色能够连接起来的边搞到一个集合里面.
然后用这个颜色的并查集结果来离线更新答案, 更新的时候, 分两种情况,
1. 这个颜色的边个数大于 lim
2. 这个颜色的边小于等于 lim
PS. lim的取值会影响效率, 具体分析见下面
1. 这种情况下, 我们令ans[k]为当前第k个询问的答案, 更新答案的时候就直接遍历每个询问, 如果询问的两个节点在一个并查集内, 则这个询问的答案 + 1, 也就是ans[k] ++;
2. 这种情况下要稍微复杂一点点.
我们需要一个辅助的map <pair<int, int>, int> M;
初始化的时候遍历 每个询问 q[i][2], 令M[ make_pair(q[i][0], q[i][1]) ] = M[ make_pair(q[i][1], q[i][0]) ] = 0;
然后我们准备把这种情况下的答案保存在M中.
具体的方法是遍历这个颜色的所有边, 取出这些边相连的所有节点放到一个集合S里.
现在再遍历S中的每个节点对(a, b), 如果M.count((a, b)) == 1, 那么 M[(a, b)] ++, M[(b, a)] ++;
最后对于每个询问k, 假设他询问的是节点a和b, 那么其答案就是, ans[k] + M[(a, b)]
效率分析
1. 这种情况下, 每次更新的复杂度是 O(Q), 其中Q是询问的个数
2. 这种情况下, 每次更新的复杂度是 O(lim*lim*log(Q)); lim*lim即是点对的个数, log(Q)是更新M的复杂度.
于是总复杂度就是 Q*A1 + lim*lim*log(Q)*A2, 其中 A1, A2分别为情况1和情况2的个数.
根据分类的定义, 可知A1 <= M / lim.
于是我们可以估计lim的值来计算各种情况下的总效率.
最后可以发现当lim在30左右的时候, 效果不错.
下面是代码
#include <stack> #include <stdio.h> #include <iostream> #include <string.h> #include <vector> #include <math.h> #include <queue> #include <map> #include <set> #include <algorithm> using namespace std; #define FOR(i, j, k) for(int i=(j);i<=(k);i++) #define REP(i, n) for(int i=0;i<(n);i++) #define mst(x, y) memset(x, y, sizeof(x)); #define pii pair<int, int> #define fr first #define sc second #define left myleft #define right myright #define ll long long #define ull unsigned long long #define seed 1331 #define mod ((int)1e9+7) #define eps 1e-5 #define pdd pair<double, double> const int lim = 30; int n, m, ans[100009]; vector <pii > E[100009], query; map <pii, int> M; int fa[100009]; stack <int> tmp; int find_(int u){ if(fa[u] == u) return u; return fa[u] = find_(fa[u]); } void merge_(int a, int b){ int ffa = find_(a), ffb = find_(b); if(ffa == ffb) return ; fa[ffa] = ffb; tmp.push(ffa); } int main(){ // freopen("2", "r", stdin); cin>>n>>m; FOR(i, 1, m){ int a, b, c; scanf("%d %d %d", &a, &b, &c); E[c].push_back(pii(a, b)); } int Q; cin>>Q; REP(i, Q){ int a, b; scanf("%d %d", &a, &b); query.push_back(pii(a, b)); M[pii(a, b)] = M[pii(b, a)] = 0; } FOR(i, 1, n) fa[i] = i; vector <int> id; FOR(i, 1, m) if(E[i].size()){ REP(j, E[i].size()) merge_(E[i][j].fr, E[i][j].sc); if(E[i].size() >= lim){ REP(k, Q) ans[k] += find_(query[k].fr) == find_(query[k].sc); }else{ id.clear(); REP(j, E[i].size()) id.push_back(E[i][j].fr), id.push_back(E[i][j].sc); sort(id.begin(), id.end()); int p = unique(id.begin(), id.end()) - id.begin(); REP(j, p) FOR(k, 0, j-1){ int a = id[j], b = id[k]; int t = find_(a) == find_(b); if(t && M.count(pii(a, b))){ M[pii(a, b)] ++; M[pii(b, a)] ++; } } } while(!tmp.empty()){ int x = tmp.top(); tmp.pop(); fa[x] = x; } } REP(i, Q) printf("%d\n", ans[i] + M[pii(query[i].fr, query[i].sc)]); return 0; }
相关文章推荐
- codeforces 286 div2 B
- Codeforces 286 div2 a
- 第二十六次codeforces竞技结束 #286 Div 2
- codeforces-div1-286-B
- codeforces 286 div2
- Codeforces Beta Round #31 (Div. 2, Codeforces format)——C
- codeforces 166 Div2 C
- [DP] Codeforces 150D #107 (Div. 1) D. Mission Impassable
- Codeforces 453 B Little Pony and Harmony Chest(Round 259 div.1 B/div.2 D)
- 第二十七次codeforces竞技结束 #288 Div 2
- codeforces 170 div2 C
- codeforces基础题——#361(div2)D
- 【codeforces 434 div 1 A】Did you mean...
- Codeforces Round #425 (Div. 2) Problem C Strange Radiation (Codeforces 832C) - 二分答案 - 数论
- CodeForces:#448 div2 a Pizza Separation
- Codeforces 715A & 716C Plus and Square Root【数学规律】 (Codeforces Round #372 (Div. 2))
- 【Codeforces Round #372 (Div. 2)】Codeforces 716B Complete the Word
- Codeforces Round #427 (Div. 2) Problem A Key races (Codeforces 835 A)
- Codeforces - 337C(div2) - Harmony Analysis
- CodeForces 373(div2)