Number of squares (multi-process DP)

Source: Internet
Author: User

[Problem description]

Square plot with N * n (n <= 10, we fill in some squares in a positive integer, and other squares in a number 0. As shown in (see example ):

A person starts from the point in the upper left corner of the graph and can walk down or right until the B point in the lower right corner. On the way he walked, he could take away the number from the square (the square after the square is removed will become a number 0 ).

This person takes two steps from A.M. To a.m. and tries to find two such paths to maximize the sum of the obtained numbers.

[Input file]

The first line of the input is an integer N (representing the square map of N * n). The next line has three integers, the first two represent positions, and the third number is the number placed on this position. A single row of 0 indicates that the input is complete.

[Output file]

Only one integer is output, indicating the maximum sum obtained from the two paths.

[Input example]

8

2 3 13

2 6 6

3 5 7

4 4 14

5 2 21

5 6 4

6 3 15

7 2 14

0 0 0

[Output example]

67

[Problem Analysis]

This is a classic multi-process dynamic planning question. If we take it only once, its model is the street problem we mentioned earlier. It can be implemented simply. What should I do if I want to fetch the data twice?

A natural idea is: assign all the preceding numbers to 0, and then take them once. It feels quite right, and the sample has passed.

However, this is wrong. The first fetch is obviously the maximum value, but the second fetch is not necessarily large, so two non-maximum paths may exist, it may be better than a smaller path.

Let's look at an example:

0 0 2 0 30 0 0 2 0 3 0

0 0 2 0 0 00 2 0 0 0

0 0 2 0 20 0 2 0 2 0

0 0 0 0 20 0 0 0 2 0

0 0 0 0 20 0 0 0 2 0

0 0 2 0 20 0 2 0 2 0

Figure 1 Figure 2

For example, figure 1 shows an appeal solution. In the figure, the red route is the maximum value obtained first. Obviously, the red and purple paths in Figure 1 are not as large as the blue and green paths.

Now that this cannot be done, we have to go back to the essence of dynamic planning to look at the generation problem. We are thinking about the status of this problem. If we go once, it is a state to go to any position in the matrix, if you go twice, it is obvious that the path to a matrix is only a part of the state, and the entire state cannot be fully described. The other part is clearly the second place. If we combine these two parts, it is a complete state.

Therefore, the design of an OPT [I1, J1, I2, J2] State indicates the maximum value obtained when the two paths go to (I1, J1) and (I2, J2) respectively. Obviously, there are four rows in the decision (multiplication principle: one vertex, two types * two rows of the other vertex)

That is, (upper, upper) (upper, left) (Left, upper) (Left, left) and left indicate the direction from which to go To the point. Of course, pay attention to walking to the same row and column, the same point (because the path is required to be unique ).

[Status] f [I] [J] [k] [l] indicates the sum of the numbers obtained by (I, j) and (k, L) respectively. G [I] [J] indicates the number in the square.

[Equation]F [I] [J] [k] [l] = max {f [I-1] [J] [k-1] [L], f [I-1] [J] [k] L-1], F [I] [J-1] [k-1] [L], f [I] [J-1] [k] [L-1]} + G [I] [J] + (I = K & J = L? 0: G [k] [l])

#include<cstdio>#include<cstring>#include<algorithm>using namespace std;int a[11][11];int dp[11][11][11][11];const int INF = 999999999;int operDp(int n){    int i1, j1, i2, j2;    memset(dp,0,sizeof(dp));    for(i1 = 1; i1 <= n; i1++)    for(j1 = 1; j1 <= n; j1++)    for(i2 = 1; i2 <= n; i2++)    for(j2 = 1; j2 <= n; j2++)    {        int tmp = -INF;        tmp = max(tmp, dp[i1-1][j1][i2-1][j2]);        tmp = max(tmp, dp[i1-1][j1][i2][j2-1]);        tmp = max(tmp, dp[i1][j1-1][i2-1][j2]);        tmp = max(tmp, dp[i1][j1-1][i2][j2-1]);        if(i1 == i2 && j1 == j2)            dp[i1][j1][i2][j2] = tmp + a[i1][j1];        else            dp[i1][j1][i2][j2] = tmp + a[i1][j1] + a[i2][j2];    }    return dp[n][n][n][n];}int main(){    int n, r, c, v;    while(scanf("%d",&n) != EOF)    {        memset(a,0,sizeof(a));        while(true)        {            scanf("%d%d%d",&r,&c,&v);            if(!r && !c && !v) break;            a[r][c] = v;        }        printf("%d\n",operDp(n));    }    return 0;}

Since the data size in this question is small, the (N ^ 4) method can also be used. However, when the scale increases, we must optimize the algorithm.

Obviously, the four-dimensional status of DP [I1] [J1] [I2] [J2] describes all possible steps. Of course, we can also change the State representation to reduce the dimension of the State.

F [k] [I] [J] = max {f [k-1] [I] [J], F [k-1] [I-1] [J-1], f [k-1] [I-1] [J], F [k-1] [I] [J-1]} + (I = J? A [k-I] [I]: A [k-I + 1] [I] + A [k-J + 1] [J])

F [k] [I] [J] indicates that step K is taken, step I is taken from the first line to the right, and step J is taken from the second line to the right.

Each path can be obtained from its top or left, so there are four states in max. And
If the two paths are in the same position, the number of the path is added only once.

#include<cstdio>#include<cstring>#include<algorithm>using namespace std;int a[11][11];int dp[21][11][11];const int INF = 999999999;int operDp(int n){    int i, j, k;    memset(dp,0,sizeof(dp));    for(k = 1; k <= 2 * n; k++)    for(i = 1; i <= k; i++)    for(j = 1; j <= k; j++)    {        int tmp = -INF;        tmp = max(tmp, dp[k-1][i-1][j-1]);        tmp = max(tmp, dp[k-1][i-1][j]);        tmp = max(tmp, dp[k-1][i][j-1]);        tmp = max(tmp, dp[k-1][i][j]);        if(i == j) dp[k][i][j] = tmp + a[k-i+1][i];        else dp[k][i][j] = tmp + a[k-i+1][i] + a[k-j+1][j];    }    return dp[2*n][n][n];}int main(){    int n, r, c, v;    while(scanf("%d",&n) != EOF)    {        memset(a,0,sizeof(a));        while(true)        {            scanf("%d%d%d",&r,&c,&v);            if(!r && !c && !v) break;            a[r][c] = v;        }        printf("%d\n",operDp(n));    }    return 0;}

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.