# 题意
n头牛,每头牛有一个开始吃草的时间和结束吃草的时间,当两头牛之间存在交点的时候,这两头牛不能安排在同一个畜栏吃草,求需要的最小畜栏数目和每头牛对应的畜栏方案
# 题解
1) 将所有牛按开始吃草的时间排序;
2) 用小根堆维护当前所有畜栏的最后一头牛的吃草结束时间;
3) 如果当前的牛可以安排在右边界最小的中,则将其安排进去,否则最小的都加不进去其他的更不可能加进去,入堆即可;
时间复杂度
排序的时间复杂度是 O(nlogn)。
依次枚举每头牛的过程中,只涉及到常数次堆的操作,时间复杂度至多是 O(logn)。
所以总时间复杂度是 O(nlogn)。
1 #include<bits/stdc++.h> 2 #define ll long long 3 #define ld long double 4 #define fi first 5 #define se second 6 #define pii pair<int,int> 7 using namespace std; 8 const int N=5e4+10; 9 int ans[N]; 10 priority_queue<pii,vector<pii>,greater<pii>> h; 11 struct node{ 12 int l,r; 13 int id,ans; 14 bool operator < (const node a) const { 15 return l<a.l; 16 } 17 }cow[N]; 18 int n; 19 int main(){ 20 ios::sync_with_stdio(0); 21 cin.tie(0); 22 cout.tie(); 23 cin>>n; 24 for(int i = 1; i <= n; i++) { 25 cin >> cow[i].l >> cow[i].r; 26 cow[i].id=i; 27 } 28 sort(cow+1,cow+1+n); 29 for(int i = 1; i <= n; i++){ 30 int num=h.size(); 31 if(num && h.top().fi < cow[i].l) { 32 cow[i].ans=h.top().se; 33 h.pop(); 34 h.push({cow[i].r,cow[i].ans}); 35 continue; 36 } 37 cow[i].ans=++num; 38 h.push({cow[i].r,num}); 39 } 40 cout<<h.size()<<endl; 41 for(int i=1;i<=n;i++) 42 ans[cow[i].id]=cow[i].ans; 43 for(int i = 1; i <= n; i++) 44 cout<<ans[i]<<endl; 45 }