洛谷P1248 加工生产调度
流水作业调度问题
有个作业要在两台机器和组成的流水线上完成加工。每个作业都必须先花时间在上加工,然后花时间在上加工。
确定个作业的加工顺序,使得从作业1在机器上加工开始到作业在机器上加工完为止所用的总时间最短。
【算法】
直观上,最优调度一定让没有空闲,的空闲时间尽量短。
Johnson算法:设为的作业集合,为的作业集合,将的作业按非减序排序,中的作业按照非增序排序,则作业接作业构成最优顺序。
算法的程序易于实现,时间复杂度为,正确性需要证明。
P1248 加工生产调度
【问题描述】
某工厂收到了个产品的订单,这个产品分别在、两个车间加工,并且必须先在加工后才可以送到车间加工。
某个产品在、两车间加工的时间分别为、。怎样安排这个产品的加工顺序,才能总的加工时间最短?
这里所说的加工时间是指:从开始加工第一个产品到所有的产品都已在两车间加工完毕的时间。
【输入格式】
第一行仅一个数据(0<<1000),表示产品的数量。
接下来个数据是表示这个产品在车间加工,各自所要的时间(都是整数)。最后的个数据是表示这个产品在车间加工,各自所要的时间(都是整数)
【输出格式】
第一行一个数据,表示最短的加工时间。
第二行是一种用时最短的产品加工顺序。
【样例输入】
5
3 5 8 7 10
6 2 1 4 9
【样例输出】
34
1 5 4 2 3
【思路】
求一个加工顺序使得加工总用时最短,就是让机器的空闲时间最短。一旦机器开始加工,则机器将会不停地进行作业,关键是机器在加工过程中有可能要等待机器。很明显第一个部件在机器上加工时,机器必须等待,最后一个部件在机器上加工时,机器也在等待机器的完工。
可以大胆猜想,要使机器总的空闲时间最短就要把在机器上加工时间最短的部件最先加工,这样使得机器能在最短的空闲时间内开始加工;把在机器上加工时间最短的部件放在最后加工,这样使得机器用最短时间等待机器完工。
于是我们可以设计出这样的贪心策略:设将按照从小到大的顺序排序,然后从第1个开始处理,若,则将它排在从头开始的作业后面,若,则将它排在从尾开始的作业前面。
例如:
=5,
,
,
则,
排序之后为。
处理: ∵ ,∴排在后面;加入之后的加工顺序为;
处理: ∵ ,∴排在后面;加入之后的加工顺序为;
处理: ∵ ,∴排在前面;加入之后的加工顺序为;
处理: ∵ ,∴排在后面;加入之后的加工顺序为;
处理: ∵ ,∴排在后面;加入之后的加工顺序为;
则最优加工顺序就是,最短时间为34。
显然这个结果是最优解。
问题是这种贪心策略是否正确呢?还需证明。
【证明】
去年刚学OI时写的(萌新刚学OI),字写得渣。
Code
#include<bits/stdc++.h>
using namespace std;
const int N = 2005;
struct data {
int id,a,b;
} J[N], ans[N];
int n;
inline bool cmp(const data &A, const data &B) {//Jhonson不等式排序
return min(A.a, A.b) < min(B.a, B.b);
}
int main() {
scanf("%d", &n);
for(int i = 1; i <= n; ++i) {
scanf("%d", &J[i].a);
J[i].id = i;//原数组下标
}
for(int i = 1; i <= n; ++i) scanf("%d", &J[i].b);
sort(J + 1, J + 1 + n, cmp);
for(int i = 1, p = 1, q = n; i <= n; ++i) {//p--队头 q--队尾
if(J[i].a <= J[i].b) ans[p++] = J[i];
else ans[q--] = J[i];
}
int time1 = 0, time2 = 0;//time1--A机器上加工用时 time2--B机器上加工用时
for(int i = 1; i <= n; ++i) {
time1 += ans[i].a;//第i件产品在A机器上所用时间
time2 = max(time1, time2);//在A机器上加工完才能到B机器 未加工完需要等待
time2 += ans[i].b;//第i件产品在B机器上所用时间
}
printf("%d\n", time2);//最后一件在B机器加工完的时刻为结束时刻
for(int i = 1; i <= n; ++i) printf("%d ", ans[i].id);//输出方案
return 0;
}
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 按钮权限的设计及实现
· 25岁的心里话