HDU 4735 Little Wish~ lyrical step~(DLX搜索)(2013 ACM/ICPC Asia Regional Chengdu Online)
2013-09-18 14:41
501 查看
Description
N children are living in a tree with exactly N nodes, on each node there lies either a boy or a girl. A girl is said to be protected, if the distance between the girl and her nearest boy is no more than D. You want to do something good, so that each girl on the tree will be protected. On each step, you can choose two nodes, and swap the children living on them. What is the minimum number of steps you have to take to fulfill your wish?
Input
The first line has a number T (T <= 150) , indicating the number of test cases. In a case, the first line contain two number n (1 <= n <= 50), D (1 <= D <= 10000000), Which means the number of the node and the distance between the girls and boys. The next lines contains n number. The i th number means the i th node contains a girl or a boy. (0 means girl 1 means boy), The follow n - 1 lines contains a, b, w, means a edge connect a th node and b th node, and the length of the edge is w (1 <= w <= 10000000).
Output
For every case, you should output "Case #t: " at first, without quotes. The t is the case number starting from 1. Then follows the answer, -1 meas you can't comlete it, and others means the minimum number of the times.
题目大意:一棵树上有n个结点,每个结点有一个男生或者一个妹纸,每条边有一个距离,问最少交换多少个人,使得妹纸在距离D内至少有一个男生。。。
思路:换句话说,这题可以理解为:交换多少个0或1,使得每个结点在D的距离内有一个1(1的男孩纸)。
那么用DLX搜索,每一列代表一个点。每一行代表一个点,每行的结点为这个点为1可以保护的所有点(包括自己)。
然后套DLX。
加入两个剪枝:搜索到的交换若大于当前答案,则剪枝。在每一层作一个乐观估计,估计最少还需要选出多少个点,若大于点为1的点数,则剪枝。
这题正解大概为DP。我不会。
代码(1171MS):
View Code
N children are living in a tree with exactly N nodes, on each node there lies either a boy or a girl. A girl is said to be protected, if the distance between the girl and her nearest boy is no more than D. You want to do something good, so that each girl on the tree will be protected. On each step, you can choose two nodes, and swap the children living on them. What is the minimum number of steps you have to take to fulfill your wish?
Input
The first line has a number T (T <= 150) , indicating the number of test cases. In a case, the first line contain two number n (1 <= n <= 50), D (1 <= D <= 10000000), Which means the number of the node and the distance between the girls and boys. The next lines contains n number. The i th number means the i th node contains a girl or a boy. (0 means girl 1 means boy), The follow n - 1 lines contains a, b, w, means a edge connect a th node and b th node, and the length of the edge is w (1 <= w <= 10000000).
Output
For every case, you should output "Case #t: " at first, without quotes. The t is the case number starting from 1. Then follows the answer, -1 meas you can't comlete it, and others means the minimum number of the times.
题目大意:一棵树上有n个结点,每个结点有一个男生或者一个妹纸,每条边有一个距离,问最少交换多少个人,使得妹纸在距离D内至少有一个男生。。。
思路:换句话说,这题可以理解为:交换多少个0或1,使得每个结点在D的距离内有一个1(1的男孩纸)。
那么用DLX搜索,每一列代表一个点。每一行代表一个点,每行的结点为这个点为1可以保护的所有点(包括自己)。
然后套DLX。
加入两个剪枝:搜索到的交换若大于当前答案,则剪枝。在每一层作一个乐观估计,估计最少还需要选出多少个点,若大于点为1的点数,则剪枝。
这题正解大概为DP。我不会。
代码(1171MS):
#include <cstdio> #include <cstring> #include <iostream> #include <algorithm> #include <vector> using namespace std; const int MAXN = 55; const int MAXC = MAXN; const int MAXR = MAXN; const int MAXP = MAXR * MAXN + MAXC; int boy[MAXN]; int mat[MAXN][MAXN]; int n, D, boys; struct DLX { int n, sz;//列数,结点总数 int sum[MAXC];//每列拥有的结点数 int row[MAXP], col[MAXP];//结点所在的行和列 int left[MAXP], right[MAXP], up[MAXP], down[MAXP];//十字链表 int ans, anst[MAXR]; void init(int nn) { n = nn; for(int i = 0; i <= n; ++i) { up[i] = down[i] = i; left[i] = i - 1; right[i] = i + 1; col[i] = i; } right = 0; left[0] = n; sz = n + 1; memset(sum, 0, sizeof(sum)); } void add_row(int r, vector<int> &columns) { int first = sz; for(int i = 0, len = columns.size(); i < len; ++i) { int c = columns[i]; left[sz] = sz - 1; right[sz] = sz + 1; down[sz] = c; up[sz] = up[c]; down[up[c]] = sz; up[c] = sz; row[sz] = r; col[sz] = c; ++sum[c]; ++sz; } right[sz - 1] = first; left[first] = sz - 1; } void remove(int c) { for(int i = down[c]; i != c; i = down[i]) { left[right[i]] = left[i]; right[left[i]] = right[i]; } } void restore(int c) { for(int i = down[c]; i != c; i = down[i]) { left[right[i]] = i; right[left[i]] = i; } } bool vis[MAXC]; int A() { memset(vis, 0, sizeof(vis)); int ret = 0; for(int i = right[0]; i != 0; i = right[i]) if(!vis[i]) { ++ret; for(int j = down[i]; j != i; j = down[j]) { for(int k = right[j]; k != j; k = right[k]) vis[col[k]] = true; } } return ret; } void dfs(int dep) { if(dep + A() > boys) return ; int tmp = 0; for(int i = 0; i < dep; ++i) tmp += boy[anst[i]]; if(dep - tmp >= ans) return ; if(right[0] == 0) { ans = dep - tmp; return ; } int c = right[0]; for(int i = right[0]; i != 0; i = right[i]) if(sum[i] < sum[c]) c = i; for(int i = down[c]; i != c; i = down[i]) { anst[dep] = row[i]; remove(i); for(int j = right[i]; j != i; j = right[j]) remove(j); dfs(dep + 1); for(int j = left[i]; j != i; j = left[j]) restore(j); restore(i); } } bool solve() { ans = n + 1; dfs(0); return ans != n + 1; } } S; void floyd() { for(int k = 1; k <= n; ++k) for(int i = 1; i <= n; ++i) if(mat[i][k] <= D) for(int j = 1; j <= n; ++j) if(mat[k][j] <= D) mat[i][j] = min(mat[i][j], mat[i][k] + mat[k][j]); } int main() { int T; scanf("%d", &T); for(int t = 1; t <= T; ++t) { scanf("%d%d", &n, &D); memset(mat, 0x3f, sizeof(mat)); boys = 0; for(int i = 1; i <= n; ++i) scanf("%d", &boy[i]), boys += boy[i]; for(int i = 1; i < n; ++i) { int u, v, c; scanf("%d%d%d", &u, &v, &c); mat[u][v] = mat[v][u] = c; } for(int i = 1; i <= n; ++i) mat[i][i] = 0; floyd(); S.init(n); for(int i = 1; i <= n; ++i) { vector<int> columns; for(int j = 1; j <= n; ++j) if(mat[i][j] <= D) columns.push_back(j); S.add_row(i, columns); } bool flag = S.solve(); printf("Case #%d: ", t); if(flag) printf("%d\n", S.ans); else puts("-1"); } }
View Code
相关文章推荐
- HDU 4737 A Bit Fun(2013 ACM/ICPC Asia Regional Chengdu Online)
- HDU 4731 Minimum palindrome 找规律 (2013 ACM/ICPC Asia Regional Chengdu Online 1004)
- hdu 4734 F(x)2013 ACM/ICPC Asia Regional Chengdu Online
- hdu 4734 F(x) 数位dp (2013 ACM/ICPC Asia Regional Chengdu Online 1007)
- HDU 4729 An Easy Problem for Elfness(主席树)(2013 ACM/ICPC Asia Regional Chengdu Online)
- hdu 4737 A Bit Fun || 2013 ACM/ICPC Asia Regional Chengdu Online || 简单题
- 2013 ACM/ICPC Asia Regional Chengdu Online HDU 4731 Minimum palindrome(规律)
- hdu 4731 Minimum palindrome 找规律 (2013 ACM/ICPC Asia Regional Chengdu Online 1004)
- hdu 4737 A Bit Fun 数列(2013 ACM/ICPC Asia Regional Chengdu Online 1010)
- hdu 4731 Minimum palindrome 找规律 (2013 ACM/ICPC Asia Regional Chengdu Online 1004)
- hdu 4038 Stone The 36th ACM/ICPC Asia Regional Chengdu Site —— Online Contest
- HDU 4715 Difference Between Primes && 2013 ACM/ICPC Asia Regional Online —— Warmup
- hdu 4750 Count The Pairs 并查集+二分+递推(2013 ACM/ICPC Asia Regional Nanjing Online 1003)
- HDU 4710 Balls Rearrangement && 2013 ACM/ICPC Asia Regional Online —— Warmup
- HDU 4717 The Moving Points(三分法)(2013 ACM/ICPC Asia Regional Online ―― Warmup2)
- 2013 ACM/ICPC Asia Regional Chengdu Online
- hdu 4722 Good Numbers 2013 ACM/ICPC Asia Regional Online —— Warmup2
- 2013 ACM/ICPC Asia Regional Nanjing Online hdu 4751 补图+二分图染色判定
- 2013 ACM/ICPC Asia Regional Chengdu Online 1004 Minimum palindrome
- 2013 ACM/ICPC Asia Regional Chengdu Online