usaco A Game Java dp

/*
ID: daniel.20
LANG: JAVA
TASK: game1
*/

import java.util.*;
import java.io.*;

public class game1 {
    static int num;
    static int numbers[] = new int[111];
    static int[][] result = new int[111][111];
    static int[][] sum = new int[111][111];

    static void dp() throws IOException{
        PrintWriter out = new PrintWriter(new BufferedWriter(new FileWriter("game1.out")));
        for(int i=1;i<=num;i++){
            result[i][i] = numbers[i];
            for(int j=i;j<=num;j++){
                sum[i][j] = sum[i][j-1]+numbers[j];
            }
        }
        //Dumper.print_2_arr(sum, num, num);
        for(int i=num;i>=1;i--){
            for(int j=i;j<=num;j++){
                result[i][j] = sum[i][j] - Math.min(result[i+1][j], result[i][j-1]);
            }
        }
        out.println(result[1][num]+" "+Math.min(result[1][num-1],result[2][num]));
        out.close();
        //Dumper.print_2_arr(result, num+1, num+1);
    }
    public static void main(String[] args) throws Exception {
        Scanner cin = new Scanner(new File("game1.in"));
        num = cin.nextInt();
        for(int i=1;i<=num;i++){
            numbers[i] = cin.nextInt();
        }
        dp();
    }
}

dp是很明显的,每个人只有两个选择,拿左边的或者右边的,就是 num[i] + dp[i-1][j] 或者 num[j] + dp[i][j-1];

但是这么编程很难写,需要一点想象力,转化为sum[i][j] - min(dp[i-1][j], dp[i][j-1])

注意这里必须是min, 根据博弈来说,前一个人必须让后一个拿最小值 这样才能让sum[i][j] - dp值最大.


代码写的时候要从最后一行开始往上推, 要注意.


你可能感兴趣的:(java,numbers,exception,import,string,class,USACO)