NYOJ 12:噴水裝置(二)(貪心,區間覆蓋問題)
阿新 • • 發佈:2018-12-16
12-噴水裝置(二)
- 記憶體限制:64MB 時間限制:3000ms 特判: No
- 通過數:28 提交數:109 難度:4
題目描述:
有一塊草坪,橫向長w,縱向長為h,在它的橫向中心線上不同位置處裝有n(n<=10000)個點狀的噴水裝置,每個噴水裝置i噴水的效果是讓以它為中心半徑為Ri的圓都被潤溼。請在給出的噴水裝置中選擇儘量少的噴水裝置,把整個草坪全部潤溼。
輸入描述:
第一行輸入一個正整數N表示共有n次測試資料。 每一組測試資料的第一行有三個整數n,w,h,n表示共有n個噴水裝置,w表示草坪的橫向長度,h表示草坪的縱向長度。 隨後的n行,都有兩個整數xi和ri,xi表示第i個噴水裝置的的橫座標(最左邊為0),ri表示該噴水裝置能覆蓋的圓的半徑。
輸出描述:
每組測試資料輸出一個正整數,表示共需要多少個噴水裝置,每個輸出單獨佔一行。 如果不存在一種能夠把整個草坪溼潤的方案,請輸出0。
樣例輸入:
2 2 8 6 1 1 4 5 2 10 6 4 5 6 5
樣例輸出:
1 2
思路
因為所有的噴水裝置都在橫向中心線上,所以可以利用圓與草坪邊界的交點來轉換成區間覆蓋問題
AC程式碼
/* * @Author: WZY * @School: HPU * @Date: 2018-10-20 15:19:19 * @Last Modified by: WZY * @Last Modified time: 2018-10-20 17:38:13 */ #include <stdio.h> #include <string.h> #include <iostream> #include <algorithm> #include <math.h> #include <limits.h> #include <map> #include <stack> #include <queue> #include <vector> #include <set> #include <string> #include <time.h> #define ll long long #define ull unsigned long long #define ms(a,b) memset(a,b,sizeof(a)) #define pi acos(-1.0) #define INF 0x7f7f7f7f #define lson o<<1 #define rson o<<1|1 #define bug cout<<"---------"<<endl #define debug(...) cerr<<"["<<#__VA_ARGS__":"<<(__VA_ARGS__)<<"]"<<"\n" const double E=exp(1); const int maxn=1e6+10; const int mod=1e9+7; using namespace std; struct wzy { double l,r; }p[maxn]; double x[maxn],r[maxn]; bool cmp(wzy u,wzy v) { if(u.l==v.l) return u.r>v.r; return u.l<v.l; } inline double MAX(double a,double b) { return a>b?a:b; } inline double MIN(double a,double b) { return a<b?a:b; } int main(int argc, char const *argv[]) { ios::sync_with_stdio(false); #ifndef ONLINE_JUDGE freopen("in.txt", "r", stdin); freopen("out.txt", "w", stdout); double _begin_time = clock(); #endif int t; int n,w,h; cin>>t; while(t--) { cin>>n>>w>>h; double res=h/2.0; double _; for(int i=0;i<n;i++) { cin>>x[i]>>r[i]; if(r[i]<=res) _=0.0; else _=sqrt(r[i]*r[i]*1.0-res*res*1.0); p[i].l=x[i]-_; p[i].r=x[i]+_; } sort(p,p+n,cmp); int ans=0; double vis=0.0; double __; for(int i=0;i<n;i++) { cout<<"====="<<vis<<endl; if(p[i].l<=vis) { __=p[i].r; cout<<" "<<__<<"~~~~~"<<p[i].l<<endl; while(p[i].l<=vis) { __=MAX(p[i].r,__); cout<<"-=-=-="<<_<<endl; i++; if(i==n) break; } vis=__; i--; ans++; } if(vis>=w) break; } if(vis>=w) cout<<ans<<endl; else cout<<0<<endl; } #ifndef ONLINE_JUDGE double _end_time = clock(); printf("time = %lf ms.", _end_time - _begin_time); #endif return 0; }