SOJ 1717 Computer (单机任务调度)
一、题目描述
Constraints :Time Limit: 2 secs, Memory Limit: 32 MB
Description:
We often hear that computer is a magic, a great invention, or even a marvel. But actually computer is just a tool people use everyday. It is a machine that can help people to process many jobs effectively. Moreover, without computer, you can not play ICPC. So, guys, let’s study some stuff about computer here.
One computer has one CPU (Central Processing Unit). CPU can be idle or processing one job at any time. Jobs come randomly and are stored in the memory until finished. CPU will process jobs according to some strategies. The processing job can be interrupted and saved back so that CPU can be available for other jobs.
Each job has a release time and a processing time. Assume that we know the schedule of all jobs, please generate a program to minimize the sum of completion times of all jobs using a strategy which assigns and interrupts jobs properly.
For example, suppose there are two jobs to be completed. Job 1 is released at time 1 and needs 4 time units to process. Job 2’s release time and processing time is 3 and 1. Figures below show three solutions:

Figure 1 shows a solution with the total complete time 4 + 6 = 10, and the result of Figure 2 and 3 are both 5 + 6 = 11. In fact, Figure 1 shows the optimal solution
Please note that all of the jobs will be released, interrupted and assigned in integer time unit.
Input:
Input may consist of multiple test cases.
Every test case begins with a line that contains one integer n (1<= n <= 50000) denoting the number of jobs. Each of the following n lines contains 2 integers: ri and pi, (1 <= ri <= 10^9, 1 <= pi <= 10000) denoting the release time and processing time of job i.
Input is terminated by EOF.
Output:
For every test case, print one line with an integer denoting the minimum sum of completion times.
Sample Input
2
1 4
3 1
Sample Output
10
二、问题解决
1、题意:单机任务调度,模拟CPU工作方式,CPU每个时刻只能处理一个任务,给出每个任务的release时间和process时间,设计调度算法,使所有任务完成时间总和最小。
2、思路:贪心思想,每次处理process时间最短的任务。
具体步骤:用循环模拟CPU,每个循环表示一个CPU时间。全局维护一个待处理的最小任务优先队列que,即剩余process时间短的任务优先。每次循环中:(1)取出que中top元素,将其剩余process时间减1,即CPU此时刻处理该任务,减到0则记录该任务完成时间;(2)将该时间刻release的任务加入等候队列que中。
3、代码:基于上面的思路,可以写出下面的代码。
// Problem#: 1717
#include <iostream>
#include <cstdio>
#include <queue>
#include <algorithm>
using namespace std;
const int MAX = ;
struct Job
{
int r,p;
bool operator < (const Job &job) const {
if(r == job.r) return p < job.p;
else return r < job.r;
}
};
Job jobs[MAX]; int main() {
int n;
while(scanf("%d",&n) != EOF) {
for(int i = ; i < n; ++i) {
scanf("%d%d", &jobs[i].r, &jobs[i].p);
}
sort(jobs,jobs+n); priority_queue<int,vector<int>,greater<int> > que;
long long ans = ;
int cnt = , cur = , tmp; que.push(jobs[].p);
for(long long i = jobs[].r; ;++i) {
tmp = que.top(); que.pop();
if (tmp- == ) {
ans = ans+i;
cnt += ;
if(cnt == n) break;
}
else que.push(tmp-);
while(cur < n && jobs[cur].r <= i) {
que.push(jobs[cur++].p);
}
}
printf("%lld\n",ans);
}
return ;
}
暴力代码
4、进一步分析:虽然思路对了,但上面代码明显会超时。

这时考虑加快cpu工作速度,即不是模拟CPU每个时刻处理的任务,而是考虑每个任务能否一次性完成。大概思路是这样,取出que中最小任务时间,判断在下一个任务release时刻(距离上一任务process时刻会有一段时间间隔),该任务能否完成,若能完成,就可以缩短时间间隔,继续判断下一任务;若不能完成,则将该任务process时间减去时间间隔,重新加入que,并将下一任务加入que。
代码如下:
// Problem#: 1717
#include <iostream>
#include <cstdio>
#include <queue>
#include <algorithm>
using namespace std;
const int MAX = ;
struct Job
{
int r,p;
bool operator < (const Job &job) const {
if(r == job.r) return p < job.p;
else return r < job.r;
}
};
Job jobs[MAX]; int main() {
int n;
while(scanf("%d",&n) != EOF) {
for(int i = ; i < n; ++i) {
scanf("%d%d", &jobs[i].r, &jobs[i].p);
}
sort(jobs,jobs+n); priority_queue<int,vector<int>,greater<int> > que;
long long ans = ;
int i = , cnt = , cur, tmp;
int pre = jobs[].r; //前一任务处理时刻
int cur_time = jobs[].r; //当前时刻 que.push(jobs[].p);
while(true) {
cur = que.top(); que.pop();
if (i >= n) {
cur_time += cur;
ans += cur_time;
cnt += ;
if (cnt == n) break;
continue;
}
tmp = jobs[i].r - pre;
if (cur <= tmp) {
cur_time += cur;
ans += cur_time;
cnt += ;
pre = cur_time;
if (cnt == n) break;
if (!que.empty()) continue; //时间间隔缩短,能否继续处理que中剩余任务
}else {
que.push(cur-tmp);
cur_time = jobs[i].r;
}
pre = jobs[i].r;
cur_time = pre;
while(i < n && jobs[i].r == pre)
que.push(jobs[i++].p);
} printf("%lld\n",ans);
}
return ;
}
结果超出我的想象,折磨了2个小时,感觉智商远远不够用啊!

SOJ 1717 Computer (单机任务调度)的更多相关文章
- [SOJ] 1282. Computer games (KMP)
坑爹题 1282. Computer Game Constraints Time Limit: 1 secs, Memory Limit: 32 MB Description Brian is an ...
- Quartz2.0以上版本的单机和集群
(一)Quartz单机 1.Quartz简介 Quartz是一个完全由java编写的开源作业调度框架,能实现业务的定时调度.Quartz主要有三个核心调度器.任务和触发器: ①任务-JobDetail ...
- 转载:Hadoop安装教程_单机/伪分布式配置_Hadoop2.6.0/Ubuntu14.04
原文 http://www.powerxing.com/install-hadoop/ 当开始着手实践 Hadoop 时,安装 Hadoop 往往会成为新手的一道门槛.尽管安装其实很简单,书上有写到, ...
- 【niubi-job——一个分布式的任务调度框架】----框架设计原理以及实现
引言 niubi-job的框架设计是非常简单实用的一套设计,去掉了很多其它调度框架中,锦上添花但并非必须的组件,例如MQ消息通讯组件(kafka等).它的框架设计核心思想是,让每一个jar包可以相对之 ...
- 【niubi-job——一个分布式的任务调度框架】----安装教程
niubi-job是什么 niubi-job是LZ耗时三个星期,费尽心血打造的一个具备高可靠性以及水平扩展能力的分布式任务调度框架,采用quartz作为底层的任务调度管理器,zookeeper做集群的 ...
- What Your Computer Does While You Wait
转: CPU的等待有多久? 原文标题:What Your Computer Does While You Wait 原文地址:http://duartes.org/gustavo/blog/ [注:本 ...
- Hadoop安装教程_单机/伪分布式配置_Hadoop2.6.0/Ubuntu14.04
摘自: http://www.cnblogs.com/kinglau/p/3796164.html http://www.powerxing.com/install-hadoop/ 当开始着手实践 H ...
- Hadoop安装教程_单机/伪分布式配置
环境 本教程使用 CentOS 6.4 32位 作为系统环境,请自行安装系统(可参考使用VirtualBox安装CentOS).如果用的是 Ubuntu 系统,请查看相应的 Ubuntu安装Hadoo ...
- 新一代分布式任务调度框架:当当elastic-job开源项目的10项特性
作者简介: 张亮,当当网架构师.当当技术委员会成员.消息中间件组负责人.对架构设计.分布式.优雅代码等领域兴趣浓厚.目前主导当当应用框架ddframe研发,并负责推广及撰写技术白皮书. 一.为什么 ...
随机推荐
- MVC模式与Android
MVC模式是软件工程中的一种软件架构,“Model-View-Controller”的缩写,中文翻译为“模型-视图-控制器”. MVC模式将一个交互式应用程序分为3各组件: 1.Model(模型):业 ...
- Failed to execute goal org.apache.maven.plugins:maven-compiler-plugin:3.1:compile (default-compile) on project LogTest: Compilation failure -> [Help 1]
[ERROR] Failed to execute goal org.apache.maven.plugins:maven-compiler-plugin:3.1:compile (default ...
- 1千万英国用户被Cryptolocker勒索软件瞄准
英国国家打击犯罪调查局(NCA)发布国家紧急警报,警报一场大规模的垃圾邮件,这些邮件中包含了一款名为CryptoLocker的勒索程序,把目标瞄准了1千万英国的email用户,该程序会加密用户的文档, ...
- Listview中显示不同的视图布局
import java.util.ArrayList; import android.app.Activity;import android.content.Context;import androi ...
- gbk与utf-8转换
linux: #include <iconv.h> int code_convert(char *from_charset,char *to_charset,char *inbuf,int ...
- nginx 安装与配置
centos7环境下nginx的安装 版本 0.85 tar zxvf nginx.tar.gz cd nginx ./configure // ./configure --help 查看编译选项 ...
- [SHTSC 2007] 善意的投票
我就是来复习Dinic算法的,仅10天不写,我已经退化成写一遍+调试需要接近一个小时了,当然其中不乏在网上乱逛的时间… 赞成从S源点连一条单向边,反对向T汇点连一条单向边,朋友关系连双向边. 但是总感 ...
- css文本换行相关属性及解释
本文摘自 http://www.wufangbo.com/css-qiang-zhi-huan-hang/ 强制换行与强制不换行用到的属性 我们一般控制换行所用到的CSS属性一共有三个:word-wr ...
- java运算符
赋值运算符 int num1=10; int num2=30; System.out.println(num1+num2); 算术运算符 int num=20; System.out.println( ...
- 【转】查看java类是从哪个包加载
Java的类装载器使用的是优先策略,加载类的时候先找到哪个就加载哪个.有时候我们做一个系统,当类库非常庞大的时候,类可能会出现冲突,也就是类路径中存在不同版本的两个相同的类,这往往给调试带来非常大的麻 ...