这几天快要期末考试了, 也不能新学习什么算法,但是又不怎么想复习,就按着poj上的分类做一下贪心题
1 poj 1328
这道题今年暑假的时候就看到了,一直拖到现在, 哎
题意:海岸线的一边有岛屿, 现在要在海岸线上安装雷达,岛屿与雷达的距离在d之内可被雷达限号覆盖, 求最少雷大数
思路:求出每个雷达的在海岸线上可被覆盖的区间,问题就转化为 区间选点问题
#include <cstdio>
#include <cmath>
#include <algorithm>
using namespace std;
typedef struct
{
double l;
double r;
}point;
point a[1010];
double x[1010], y[1010], d;
int n, ca = 1;
void work(int k)
{
double m = sqrt(d*d - y[k]*y[k]);
a[k].l = x[k] - m;
a[k].r = x[k] + m;
}
bool cmp(point a, point b)
{
return a.r < b.r;
}
int main()
{
while(scanf("%d %lf", &n, &d), (n+d))
{
bool flag = 0;
for(int i=1; i<=n; i++)
{
scanf("%lf %lf", &x[i], &y[i]);
if(y[i] > d)
flag = 1;
}
if(flag)
{
printf("Case %d: -1\n", ca++);
continue;
}
for(int i=1; i<=n; i++)
work(i);
sort(a+1, a+n+1, cmp);
int ans = 1;
double k = a[1].r;
for(int i=2; i<=n; i++)
if(a[i].l > k)
{
k = a[i].r;
ans++;
}
printf("Case %d: %d\n", ca++, ans);
}
return 0;
}
2 poj 2109
分类上说这次贪心题, 不过我到没有贪心的感觉
#include <cstdio>
#include <cmath>
double n, p;
int main()
{
while(scanf("%lf %lf", &n, &p) == 2)
{
printf("%.0f\n", pow(p, 1/n));
}
return 0;
}
3 poj 2586
题意:题意很难懂,后来实在看不懂看了这题的中文翻译, 这里就不阐述了
思路:1 因为只有12个月, 因此课枚举12个月的盈亏情况,进行判断(但直接枚举超时了,还是稍稍优化了一下)
#include <cstdio>
#include <algorithm>
using namespace std;
int vis[15], a, b, ans;
void dfs(int cur)
{
if(cur == 13)
{
int sum, flag = 1;
for(int i=1; i<=8; i++)
{
sum = 0;
for(int j=i; j<=i+4; j++)
{
if(vis[j])
sum += a;
else
sum -= b;
}
if(sum >= 0)
{
flag = 0;
break;
}
}
if(flag)
{
sum = 0;
for(int i=1; i<=12; i++)
if(vis[i])
sum += a;
else
sum -= b;
ans = max(ans, sum);
}
return;
}
vis[cur] = 1;
dfs(cur + 1);
vis[cur] = 0;
dfs(cur + 1);
}
int main()
{
while(scanf("%d %d", &a, &b) == 2)
{
vis[1] = 1;
ans = 0;
dfs(2);
if(ans)
printf("%d\n", ans);
else
puts("Deficit");
}
}
2 因为连续的五个月都是亏损的,故可枚举连续五个月中的盈的月数, 亏得月数为5-盈的月数
#include <cstdio>
int s, d, ans;
int main()
{
while(scanf("%d %d", &s, &d) == 2)
{
if(d > 4*s) ans = 10*s - 2*d;
else if(2*d > 3*s) ans = 8*s - 4*d;
else if(3*d > 2*s) ans = 6*s - 6*d;
else if(4*d > s) ans = 3*s - 9*d;
else ans = 0;
if(ans > 0)
printf("%d\n", ans);
else
puts("Deficit");
}
return 0;
}
4 poj 3069
没什么好说的, 水题
#include <cstdio>
#include <algorithm>
using namespace std;
int a[1010], r, n;
int binsearch(int k)
{
int l = 1, r = n;
int ans = 0;
while(l <= r)
{
int m = (l + r) / 2;
if(a[m] <= k)
{
ans = m;
l = m+1;
}
else
r = m-1;
}
return ans;
}
int main()
{
while(scanf("%d %d", &r, &n) == 2)
{
if(r==-1 && n==-1)
break;
for(int i=1; i<=n; i++)
scanf("%d", &a[i]);
sort(a+1, a+n+1);
int ans = 0;
for(int i=1; i<=n; i++)
{
int j = binsearch(a[i] + r);
ans++;
i = binsearch(a[j] + r);
}
printf("%d\n", ans);
}
return 0;
}