一、题目描述

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 (单机任务调度)的更多相关文章

  1. [SOJ] 1282. Computer games (KMP)

    坑爹题 1282. Computer Game Constraints Time Limit: 1 secs, Memory Limit: 32 MB Description Brian is an ...

  2. Quartz2.0以上版本的单机和集群

    (一)Quartz单机 1.Quartz简介 Quartz是一个完全由java编写的开源作业调度框架,能实现业务的定时调度.Quartz主要有三个核心调度器.任务和触发器: ①任务-JobDetail ...

  3. 转载:Hadoop安装教程_单机/伪分布式配置_Hadoop2.6.0/Ubuntu14.04

    原文 http://www.powerxing.com/install-hadoop/ 当开始着手实践 Hadoop 时,安装 Hadoop 往往会成为新手的一道门槛.尽管安装其实很简单,书上有写到, ...

  4. 【niubi-job——一个分布式的任务调度框架】----框架设计原理以及实现

    引言 niubi-job的框架设计是非常简单实用的一套设计,去掉了很多其它调度框架中,锦上添花但并非必须的组件,例如MQ消息通讯组件(kafka等).它的框架设计核心思想是,让每一个jar包可以相对之 ...

  5. 【niubi-job——一个分布式的任务调度框架】----安装教程

    niubi-job是什么 niubi-job是LZ耗时三个星期,费尽心血打造的一个具备高可靠性以及水平扩展能力的分布式任务调度框架,采用quartz作为底层的任务调度管理器,zookeeper做集群的 ...

  6. What Your Computer Does While You Wait

    转: CPU的等待有多久? 原文标题:What Your Computer Does While You Wait 原文地址:http://duartes.org/gustavo/blog/ [注:本 ...

  7. Hadoop安装教程_单机/伪分布式配置_Hadoop2.6.0/Ubuntu14.04

    摘自: http://www.cnblogs.com/kinglau/p/3796164.html http://www.powerxing.com/install-hadoop/ 当开始着手实践 H ...

  8. Hadoop安装教程_单机/伪分布式配置

    环境 本教程使用 CentOS 6.4 32位 作为系统环境,请自行安装系统(可参考使用VirtualBox安装CentOS).如果用的是 Ubuntu 系统,请查看相应的 Ubuntu安装Hadoo ...

  9. 新一代分布式任务调度框架:当当elastic-job开源项目的10项特性

    作者简介: 张亮,当当网架构师.当当技术委员会成员.消息中间件组负责人.对架构设计.分布式.优雅代码等领域兴趣浓厚.目前主导当当应用框架ddframe研发,并负责推广及撰写技术白皮书.   一.为什么 ...

随机推荐

  1. 解析txt文本,dom4j工具输出为xml文档

    有如下一个ttl.txt文本文档,每一行用空格隔开的三段分别代表主谓宾, 要将它们输出为xml格式文档 工具:dom4j,jar包导入MyEclipse的Java Project工程 代码如下: pa ...

  2. Ubuntu 使用Gparted工具扩大第一分区方法步骤

    Ubuntu 使用Gparted工具扩大第一分区方法步骤 环境:vmware9.01 .ubuntu12.04 需要的工具: 1.U盘,Universal-USB-Installer-1.9.6.4. ...

  3. Websocket 协议解析

    WebSocket protocol 是HTML5一种新的协议.它是实现了浏览器与服务器全双工通信(full-duplex).          现 很多网站为了实现即时通讯,所用的技术都是轮询(po ...

  4. hibernate的1+n

    对数据库访问还是必须考虑性能问题的, 在设定了1 对多这种关系之后, 查询就会出现传说中的n +1 问题. 1 )1 对多,在1 方,查找得到了n 个对象, 那么又需要将n 个对象关联的集合取出,于是 ...

  5. memcpy函数用法

    memcpy函数用法 .分类: VC++ VC++ mfc matlab 2011-12-01 19:17 14538人阅读 评论(0) 收藏 举报 null 原型:extern void *memc ...

  6. Linux下man安装及使用方法

    常用法: man [section] name 其中: section 指的是手册页的哪个部分,可以是1.2.3…8.,若不指定,man会按照次序依次查找,知道找到第一个. name 指的是某个命令. ...

  7. 如何通过JDBC访问数据库

    Java数据库连接(JDBC)用与在Java程序中实现数据库操作功能,它提供了执行SQL语句.访问各种数据库的方法,并为各种不同的数据库提供统一的操作接口,java.sql包中包含了JDBC操作数据库 ...

  8. SharePoint Site "Language Settings"功能与CSOM的对应

    博客地址:http://blog.csdn.net/FoxDave SharePoint网站中的语言设置:"Language Settings",可以用CSOM通过Site的一些 ...

  9. iOS开发(OC)中的命名规范

    开小差:最近发现自己有一个经验主义的毛病,不太容易接受新的知识,这对从事技术研发的人来说不太合理,需要改之. 正文:通过读写大量代码我有自己的一套编程思路和习惯,自认为自己的编码习惯还是不错的,代码结 ...

  10. 关于css的新思考

    因为被派去协助别的组,有机会写了一下react,发现ICE做的那一个套件用来搭建后台系统真的太给力了(插一句必入table组件其实是可以把删除添加座位基础方法加进去的).因为看了demo的代码以及对于 ...