ZOJ3471 Shape Pressure DP

Topic link: https://www.nowcoder.com/acm/contest/116/J

There are n atoms, any two atoms collide with each other will generate a certain amount of energy, and the hit one will disappear, and then ask you to ask for the maximum energy that can be generated when n atoms have n-1 hits.

Input: Contains multiple sets of instances. The first row of each instance is N (2<=N<=10), then the next N rows, each row has N integers x (0<=x<=1000), the first The jth number in the i row represents the energy generated after the i atom hits the j atom, and j disappears. When N is 0, the table input ends.

Output: Output the maximum energy value for each instance.

Analysis: This problem is very similar to the TSP problem, and can be solved using a similar state definition method.

Let d[i][S] denote the maximum energy that can be generated when the current atom i and the set of atoms that have been used is S (S includes i).

The state transition equation is:d[i][S|(1<<i)]=max{ d[j][S]+v[i][j] },用i去撞j,或d[j][S|(1<<i)]=max{d[j][S]+v[j][i] },用j去撞i

初值:d[i][1<<i]=0.

This question is wrong. There is a deviation in the meaning of the question: the meaning of this question is that any two atoms can collide, not necessarily in sequence. For example, there are 6 atoms, and now 123 atoms have collided and the remaining 3 number atom, then I can hit 5 and 6, and then hit 3 with the rest, and I don't necessarily need to hit one of {4,5,6} with 3. So the correct solution should be:

Let d[S]=x represent the maximum energy value that the atom represented in the current set S has been destroyed and can generate.

d[S+{j}]=max{ d[S]+v[i][j] }, i and j are both atoms outside the set S and hit j with i.

d[S+{i}]=max{ d[S]+v[j][i] }, i and j are both atoms outside the set S and hit i with j.

Code:

#include <bits/stdc++.h>
 
using namespace std;
 
const vector<int> v {1,2,4,8,16,32,64,128,256,512,1024,2048};
intmain()
{
    int n;
    while(scanf("%d", &n) && n) {
        vector<vector<int> >e (n, vector<int>(n));
        for(int i = 0;i < n;i ++) for(int j = 0;j < n;j ++) scanf("%d", &e[i][j]);
        vector<int>dp(v[n], 0);
        for(int i = 0;i < v[n];i ++) {
            for(int j = 0;j < n;j ++) {
                if(i & v[j]) continue;
                for(int k = 0;k < n;k ++) {
                    if(k != j && !( i & v[k] ) ) {
                        dp[i | v[j]] = max(dp[i | v[j]], dp[i] + e[k][j]);
                    }
                }
            }
        }
        int res = 0;
        for(int i = 0;i < v[n];i ++) res = max(res, dp[i]);
        printf("%d\n", res);
    }
    return 0;
}


Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=325605164&siteId=291194637