P1248 加工生产调度
Solution:
贪心神仙题。
tips: 对于贪心题目,先考虑两个东西时的情况,一般是可以扩展到多个东西的情况的。
此时我们考虑两订单
-
先
后 : -
先
后 :
此时我们按这个东西来做
为什么呢?
因为这个东西它不具有传递性。
如果仔细想想,就会发现按这个排序,对于排完序后下标递增的三个数
(然鹅这个时候我就不会了)
那么我们感性理解一下,越少时间的工序对后面的影响越小。于是我们在两个数组未被安排过的里面找最小值。
找到的最小值可能在
1.若最小值是
2.若最小值是
那么做法也就一目了然了:
-
先找到
和 中没有安排过工序中的时间最小值。 -
若最小值在
数组中,则将此工序安排在未安排工序的首部。 -
若最小值在
数组中,则将此工序安排在未安排工序的尾部。 -
求完顺序后模拟一次得到答案
code:
#include<bits/stdc++.h> #define int long long using namespace std; const int N=3e4+10; int order[N],lo,ro;// order 是安排顺序,lo、ro是左端点和右端点 int n,a[N],b[N]; struct node{ int c,id;// id 为原数组中的编号,c=min(a[i],b[i]) bool lft;// 是放在首部还是尾部 }rk[N]; bool cmp(struct node n1,struct node n2){ return n1.c<n2.c; } signed main(){ std::ios::sync_with_stdio(false); cin.tie(0);cout.tie(0); cin>>n; for(int i=1;i<=n;i++)cin>>a[i]; for(int i=1;i<=n;i++)cin>>b[i]; for(int i=1;i<=n;i++){ rk[i].id=i;rk[i].c=min(a[i],b[i]); if(rk[i].c==a[i])rk[i].lft=true;// a[i] 小则放在首部 else rk[i].lft=false;// 否则就是尾部 } sort(rk+1,rk+n+1,cmp); lo=1,ro=n; for(int i=1;i<=n;i++){ if(rk[i].lft)order[lo++]=rk[i].id; else order[ro--]=rk[i].id; } int ta=0,tb=0;// A 厂和 B 厂的最后一工序结束时间 for(int i=1;i<=n;i++){ int x=order[i]; ta+=a[x];tb=max(ta,tb)+b[x];// 直接模拟 } cout<<max(ta,tb)<<endl; for(int i=1;i<=n;i++)cout<<order[i]<<" "; return 0; }
本文作者:Little_corn
本文链接:https://www.cnblogs.com/little-corn/p/18157456
版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步