复印书本

复印书本

有M本书(编号为1,2,…,M),每本书都有一个页数(分别是P1,P2,…,PM)。
想将每本都复制一份。将这M本书分给K个抄写员(1<=K<=M<=500),每本书只能分配给一个抄写员进行复制。
每个抄写员至少被分配到一本书,而且被分配到的书必须是连续顺序的。复制工作是同时开始进行的,
并且每个抄写员复制一页书的速度都是一样的。所以,
复制完所有书稿所需时间取决于分配得到最多工作的那个抄写员的复制时间。
试找一个最优分配方案,使分配给每一个抄写员的页数的最大值尽可能小。
Input

第一行两个整数M、K;(K<=M<=500)
第二行M个整数,第i个整数表示第i本书的页数。

Output

输出为一个数,即分配给每一个抄写员的页数的最大值
Sample Input
9 3
1 2 3 4 5 6 7 8 9
Sample Output
17

题解(动态规划)

f[i][j] = min(max(f[i-l][j-1], d[i] - d[i-l]),f[i][j]);
f[i][j]得到的数是其中要为j中其中一个人的分配最大且相对均衡(对于每个人)的数
i为书数,j为人数
l为最后一个人copy的书数,i-l为j-1copy的书数
对于f[i][j]的最好的解法,就是使用f[i-l][j-1]为(j-1)中的一个人的copy的页数
max为的得到(f[i-l][j-1])和(剩下的页数)的最大因为我们结果要的到最大的那个数
min 为了避免过大使分给每个人的页数相差过大(要求我们每个人分到的要对平衡所用时间最小)

    import java.util.Scanner;
    public class copy_book {
        static int m,k;//书本,人数
        static int[] a;//第i本书有的页数
        static int[][] f;//f[i][j] i本书j个人
        static int[] d;//第i本书的总页数的d[i]
        public static void main(String[] args) {
            Scanner in = new Scanner(System.in);
            m = in.nextInt();
            k = in.nextInt();
            a = new int[m + 1];
            d = new int[m + 1];
            f = new int[m + 1][m + 1];
            for (int i = 0; i <= m; i++)
                for (int j = 0; j <=m ; j++)
                    f[i][j] = 100000;
            for (int i = 1; i <=m; i++) {
                a[i] = in.nextInt();
                d[i] = d[i - 1] + a[i];
                f[i][1] = d[i];
            }
            for (int j = 2; j <= k; j++) {
                for (int i = j; i <= m; i++) {
                    for (int l = 1; l <= i - 1; l++) {
                        if (Math.max(f[i - l][j - 1], d[i] - d[i - l]) < f[i][j])
                            f[i][j] = Math.max(f[i - l][j - 1], d[i] - d[i - l]);
                    }
                    System.out.print("f["+i+"]["+j+"]="+f[i][j]+"    ");
                }
                System.out.println();
            }
            System.out.println(f[m][k]);
    	}
    }

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值