zoukankan      html  css  js  c++  java
  • 优先队列

    定义:能够完成下列操作的数据结构叫做优先队列。

    1、插入一个数值

    2、取出最小的数值(获得数值,并且删除)

    优先队列示意图

    /*Poj 2431
     *题目大意:你需要驾驶一辆卡车行驶L单位距离。最开始时,卡车上有P单位的汽油。卡车没开1单位距离需要消耗1单位的汽油。 
     *		如果在途中车上的汽油耗尽,卡车就无法继续前行,因而无法到达终点。在途中一共有N个加油站。第i个加油站站在距离
     *		起点Ai单位距离的地方,最多可以给卡车加Bi单位汽油。假设卡车的燃料箱的容量是无限大的,无论加多少油都没有问题。
     *		那么请问卡车是否能到达终点?如果可以,最少需要加多少次油?如果可以到达终点输出最少的加油次数,否则输出-1
     *算法分析: 由于加油站的数量N非常大,必须想一个高效的解法。我们稍微变换一下思考方式。在卡车开往终点的途中,只有在加油站
     *		才可以加油。但是,如果认为“在到达加油站i时,就获得了一次在之后的任何时候都可以加Bi单位汽油的权利”,在解决问题上
     *		应该也是一样的。而在之后需要加油时,就认为是在之前经过的加油站加的油就可以了。那么,因为希望到达终点时加油次数尽可能少,
     *		所以当燃料为0了之后再进行加油看上去是一个不错的方法。在燃料为0时,应该使用哪个加油站来加油呢?显然,应该选能加油量Bi最大的
     *		加油站
     *				为了高效的进行上述操作,我们可以使用从大到小的顺序依次取出数值的优先队列。
     *		1、在经过加油站i时,往优先队列里面加入Bi。
     *		2、当燃料空了时,		a,如果优先队列也是空的,则无法到达终点
     *								b,否则取出优先队列中的最大元素,并用来给卡车加油。 
    */
    
    int L, P, N;
    int A[MAX_N+1], B[MAX_N+1];
    
    void solve() {
    	//为了写起来方便,我们把终点也认为是加油站 
    	A[N] = L;
    	B[N] = 0;
    	N ++ ;
    	//维护加油站的优先队列
    	priority_queue<int> que;
    	
    	//ans: 加油次数, pos:现在所在位置, tank:邮箱中汽油的量
    	int ans = 0, pos = 0, tank = P;
    	for (int i = 0; i<N; i++) {
    		//接下去要前进的距离
    		int d = A[i] - pos;
    		
    		//不断加油直到油量足够行驶到下一个加油站
    		while (tank - d < 0) {
    			if (que.empty()) {
    				puts("-1");
    				return ;
    			}
    			tank += que.top();
    			que.pop();
    			ans ++ ;
    		} 
    		
    		tank -= d;
    		pos = A[i];
    		que.push(B[i]);
    	} 
    	
    	printf("%d
    ",ans);
    } 


  • 相关阅读:
    【Idea】设置springboot启动环境
    python base64加密解密
    binascii.Error: Incorrect padding
    DataFrame随机采样
    检测和过滤异常值
    离散化和面元划分
    AttributeError: 'Categorical' object has no attribute 'levels'
    AttributeError: 'Categorical' object has no attribute 'labels'
    重命名轴索引
    替换值replace
  • 原文地址:https://www.cnblogs.com/Tovi/p/6194819.html
Copyright © 2011-2022 走看看