1. 程式人生 > 實用技巧 >【貪心】 Expedition

【貪心】 Expedition

題意

傳送門
需要駕車到距離\(L\)的城鎮,最開始有\(P\)單位汽油,每行駛1單位距離消耗1單位汽油,如果汽油耗盡則無法行進,路上一共有\(N\)個加油站,第\(i\)個加油站距離城鎮\(d_{i}\)個單位,可以加油\(b_{i}\)單位,每個加油站只能加一次,容量無限,求最少的加油次數抵達城鎮,如果不能抵達輸出-1

資料範圍

\(1 \leq N \leq 10000\)
\(1 \leq L \leq 1000000 , 1\leq P \leq 1000000\)
\(1 \leq d_{i} < L , 1\leq b_{i} \leq 100\)

題解

將所有的距離轉化一下,加油的時間是在無法抵達當前加油站的時候進行,每次加都貪心的加已經經過的加的最多的

Code

#include<cstdio>
#include<cmath>
#include<cstring>
#include<cstdlib>
#include<ctime>
#include<cctype>
#include<iostream>
#include<algorithm>
#include<vector>
#include<list>
#include<queue>
#include<string>
#include<set>
#include<map>
using namespace std;
#define rep(i,a,n) for(int i=a;i<n;i++)
#define per(i,a,n) for(int i=n-1;i>=a;i--)
#define fi first
#define se second 
#define ll long long
#define pb push_back
typedef pair<long long,long long> pll;
typedef pair<int,int> pii;
typedef vector<int> vi;
typedef vector<long long> vll;
typedef double db;
const ll mod=1e9+7;
ll powmod(ll a,ll b,ll p){ll res=1;a%=p;while(b){if(b&1) res=res*a%p;a=a*a%p;b>>=1;}return res;}
ll gcd(ll a,ll b) {return b?gcd(b,a%b):a;}
const int N=1e4+10;
int n;
int L,P;
pii sta[N];

int main(){
    scanf("%d",&n);
    rep(i,0,n) 
        scanf("%d%d",&sta[i].fi,&sta[i].se);
    scanf("%d%d",&L,&P);
    rep(i,0,n) 
        sta[i].fi=L-sta[i].fi;

    sort(sta,sta+n);
    priority_queue<int>q;
    int ans=0;
    sta[n]=make_pair(L,0);
    n++;
    rep(i,0,n){
        int distance=sta[i].fi,add=sta[i].se;
        while(P < distance){
            if(q.empty()){
                puts("-1");return 0;
            }
            P += q.top();
            q.pop();
            ans++;
        }
        q.push(add);
    }
    printf("%d\n",ans);
}