NOIP优先队列_接水问题

问题描述
学校里有一个水房,水房里一共装有m 个龙头可供同学们打开水,每个龙头每秒钟的 供水量相等,均为1。 现在有n 名同学准备接水,他们的初始接水顺序已经确定。将这些同学按接水顺序从1 到n 编号,i 号同学的接水量为wi。接水开始时,1 到m 号同学各占一个水龙头,并同时打 开水龙头接水。当其中某名同学j 完成其接水量要求wj 后,下一名排队等候接水的同学k 马上接替j 同学的位置开始接水。这个换人的过程是瞬间完成的,且没有任何水的浪费。即 j 同学第x 秒结束时完成接水,则k 同学第x+1 秒立刻开始接水。若当前接水人数n’不足m, 则只有n’个龙头供水,其它m−n’个龙头关闭。 现在给出n 名同学的接水量,按照上述接水规则,问所有同学都接完水需要多少秒。
Input
  第1 行2 个整数n 和m,用一个空格隔开,分别表示接水人数和龙头个数。 第2 行n 个整数w1、w2、……、wn,每两个整数之间用一个空格隔开,wi 表示i 号同 学的接水量。
Output
  输出只有一行,1 个整数,表示接水所需的总时间。
Sample Input
5 3
4 4 1 2 1

Sample Output
4
思路
用一个数组存所有的元素 优先队列存前m个元素,然后每次弹出一个最小的元素 把剩余的元素减去这个最小的元素 然后把数组中剩下的元素进入队列中。
优化
这样的话每次都要减去这个最小的元素,复杂度太高了。所以我们可以想既然弹出的是最小的 那么与此同时把这个最小的加上数组中剩下的入列后就相当于把这两个看成一个整体,下一次再弹出最小的有可能比之前那个小 因为这就相当于接水 如果把这次和下次接水的看做一个整体那么中间肯定有人水已经接完了 所以再把中间那个和下下个看做一个整体然后依次类推等到剩下的用完的时候就依次弹出最小的即可剩下那个就是答案。仔细想想这个方法好巧妙 我也是向一位优秀的学长学习的。很感谢他的帮助了。

#include
#include
#include
#define Xiaobo main
using namespace std;
int Xiaobo() 
{
	int n,m;
	priority_queue,greater > p;
	int num[10005]; 
	cin>>n>>m;
	for(int i=0;i>num[i];
		if(i

你可能感兴趣的:(Acm之旅___优先队列)