奥赛一本通 1425 加工生产调度

1425 加工生产调度

题目大意

$n$ 个产品都需要先后在 $A, B$ 两个车间加工,给出每个产品分别在两个车间的加工时间,要如何排序才能使得总时间最短。

知识要点

贪心、排序

解题思路

$A$ 车间必然是一直加工产品,最后空闲时间等待 $B$ 车间;而 $B$ 车间则可以先等待 $A$ 车间,然后一直加工完所有产品。显然加工的总时间是固定的,因此需要使空闲时间最小化。对于第一个产品,它在 $A$ 车间的加工必然最短,这样可以让 $B$ 车间等待时间少,对于最后一个产品,它在 $B$ 车间的加工必然最短,这样可以让 $A$ 车间等待时间少。不难发现,确定第一个或最后一个产品并不会影响其他产品的加工顺序,因此持续寻找加工时间的最小值将它放在前面或后面完成即可。

参考代码

#include <bits/stdc++.h>
using namespace std;

const int N = 10005;
struct Node {
    int v, i; //最小值、编号
} P[N];
int a[N], b[N], ans[N];

int main() {
    int n;
    scanf("%d", &n);
    for(int i = 1; i <= n; i++) scanf("%d", &a[i]);
    for(int i = 1; i <= n; i++) scanf("%d", &b[i]);

    for(int i = 1; i <= n; i++) P[i] = {min(a[i], b[i]), i};
    for(int i = 1; i < n; i++) for(int j = i + 1; j <= n; j++) //一本通没有设置 spj
            if(P[i].v > P[j].v) swap(P[i], P[j]);              //使用选择排序才能通过

    int l = 1, r = n; //确定前后的位置
    for(int i = 1; i <= n; i++)
        if(P[i].v == a[P[i].i]) ans[l++] = P[i].i;
        else ans[r--] = P[i].i;

    int A = 0, B = 0;
    for(int i = 1; i <= n; i++) {
        A += a[ans[i]];
        B = max(A, B) + b[ans[i]];
    }
    printf("%d\n", B);
    for(int i = 1; i <= n; i++) printf("%d ", ans[i]);
    return 0;
}
posted @ 2026-08-31 12:10  萧西待水  阅读(1)  评论(0)    收藏  举报