LOJ#10001 種樹(貪心)
阿新 • • 發佈:2018-12-31
題目描述
某條街被劃為 n 條路段,這 n 條路段依次編號為 1…n。每個路段最多可以種一棵樹。現在居民們給出了 h 組建議,每組建議包含三個整數 b,e,t 表示居民希望在路段 b 到 e之間至少要種 t 棵樹。這些建議所給路段的區間可以交叉。請問:如果要滿足所有居民的建議,至少要種多少棵樹。
輸入格式
第一行為 n,表示路段數。
第二行為 h,表示建議數。
下面 h 行描述一條建議:b,e,t 用一個空格分隔。
輸出格式
輸出只有一個數,為滿足所有居民的建議,所需要種樹的最少數量。
樣例
樣例輸入
9
4
1 4 2
4 6 2
8 9 2
3 5 2
樣例輸出
5
資料範圍與提示
30%的資料滿足 0<n≤1000,0<h≤500;
100%的資料滿足 0<n≤3×10^4,h≤5000,0<b≤e≤3×10^4,t≤e−b+1。
區間問題。按右端點的升序排序,將樹儘可能的往右端點種。
AC程式碼:
#include<iostream> #include<algorithm> #include<cstring> #include<iomanip> #include<vector> #include<stack> using namespace std; struct node { int l,r,num; friend bool operator <(node a,node b) { return a.r<b.r; } }sugg[5001];//suggestion int main() { int n,h,ans=0; bool isplan[30001];//is planted memset(isplan,0,sizeof(isplan)); cin>>n>>h; for(int i=1;i<=h;i++) cin>>sugg[i].l>>sugg[i].r>>sugg[i].num; sort(sugg+1,sugg+h+1); for(int i=1;i<=h;i++) { int t=0;//當前建議已種樹數目 for(int j=sugg[i].r;j>=sugg[i].l;j--) t+=isplan[j]; for(int j=sugg[i].r;j>=sugg[i].l&&t<sugg[i].num;j--) if(!isplan[j]) isplan[j]=1,ans++,t++; } cout<<ans; }