Link:
http://acm.hdu.edu.cn/showproblem.php?pid=3339
Topic:
Problem Description
Since 1945, when the ' the ' nuclear bomb was exploded by the ' Manhattan Project team in the US, the number of nuclear weapon s have soared across the globe.
Nowadays,the crazy Boy in Fzu named Aekdycoin, possesses some nuclear weapons and wanna our world. Fortunately, our mysterious spy-net has gotten he plan. Now, we are need to stop it.
But the arduous task is obviously isn't easy. The ' all ', we know that operating system of the nuclear weapon consists of some connected electric stations, which Forms a huge and complex electric network. Every Electric station has its power value. To-start the nuclear weapon, it must cost half of the electric ' s power. So-all, we are need to make more than half's the power diasbled. Our tanks are ready for our action in the base (ID is 0), and we must drive them on the road. As for a electric station, we control them if and only if we tanks stop there. 1 unit distance costs 1. And we have enough tanks to use.
Now we commander wants to know of the minimal oil cost in this action.
Input
The ' The ' input contains a single integer T, specifying the number of testcase in the file.
For each case, the number of the The ' n<= ' (1<=), M (1<= m<= 10000), specifying the number of the Statio NS (the IDs are 1,2,3...N), and the number of the roads between the station (Bi-direction).
Then m lines follow, each line is Interger St (0<= st<= N), ed (0<= ed<= N), dis (0<= dis<=), Specifyin G The start point, end point, and the distance between.
Then n lines follow, each line are a Interger pow (1<= pow<=), specifying the electric station ' s power by ID order .
Output
The minimal oil cost in this action.
If not exist print "impossible" (without quotes).
Sample Input
2
2 3 0 2 9 2 1 3 1 0 2 1 3 2 1 2 1 3 1-
3
Sample Output
5
Impossible
The main effect of the topic:
To destroy a power grid, there are n power stations numbered 1~n and each power station has its own energy value. There is a military base number 0, which has unlimited tanks, can drive to a power station bombing destroyed the power station, and a tank can only destroy one. Now to destroy some of these plants, the power of the grid to lose more than half of the total energy, and to allow all the tanks to carry out the mission to travel at least.
Analysis and Summary:
1. It is easy to think of the shortest distance of 0 to all other points with single-source algorithm.
2. The key is to choose which plants to destroy, so that the total energy of these destroyed power stations is more than half of the original.
Because for every power plant, either to choose to destroy, or not to destroy, then can associate with the classic 01 knapsack problem.
The sum of the shortest distance is used as the knapsack capacity, the energy value of each station as the item value, then OK.
Code:
#include <iostream> #include <cstdio> #include <cstring> #include <queue> #include <utility
> Using namespace std;
typedef pair<int, int>pii;
const int INF = 0x7fffffff;
const int VN = 105;
const int EN = 20005; struct Edge{int v,next,w;}
E[en];
Priority_queue<pii,vector<pii>,greater<pii> >q;
int n, size;
int HEAD[VN], d[vn], POW[VN];
int dp[10005];
int oil[10005];
void init () {size = 0;
Memset (Head,-1, sizeof (head));
while (!q.empty ()) Q.pop ();
} void Addedge (int u,int v,int W) {e[size].v=v, e[size].w=w;
E[size].next = Head[u];
Head[u] = size++;
} void Dijkstra (int src) {for (int i=0; i<=n; ++i) d[i] = INF;
D[SRC] = 0;
Q.push (Make_pair (d[src], SRC)); while (!q.empty ()) {PII x = Q.top ();
Q.pop ();
int u = x.second;
if (D[u]!= x.first) continue; for (int e=head[u]; e!=-1; E=e[e].next) {int tmp = D[u] + e[e].w;
if (D[E[E].V] > tmp) {D[E[E].V] = tmp;
Q.push (Make_pair (TMP,E[E].V));
int main () {int t,m,u,v,c;
scanf ("%d", &t);
while (t--) {scanf ("%d%d", &n,&m);
Init ();
for (int i=0; i<m; ++i) {scanf ("%d%d%d", &u,&v,&c);
Addedge (U,V,C);
Addedge (V,U,C);
for (int i=1; i<=n; ++i) {scanf ("%d", &pow[i]);
} Dijkstra (0);
if (D[1]==inf) {puts ("impossible"), continue;
int dis_sum = 0, pow_sum = 0;
for (int i=1; i<=n; ++i) {dis_sum + = D[i];
Pow_sum + = Pow[i];
memset (DP, 0, sizeof (DP));
for (int i=1; i<=n; ++i) for (int j=dis_sum; j>=d[i];--j) DP[J] = max (dp[j],dp[j-d[i]]+pow[i]);
Pow_sum = (pow_sum>>1) +1;
for (int i=1; i<=dis_sum; ++i) {if (dp[i]>=pow_sum) {printf ("%d\n", I);
Break
}} return 0; }
More Wonderful content: http://www.bianceng.cnhttp://www.bianceng.cn/Programming/sjjg/