POJ - 2376 贪心-区间问题

版权声明:博主的博客不值钱随便转载但要注明出处 https://blog.csdn.net/easylovecsdn/article/details/83420439

题目容易陷入的误区:

题目表面上是尽可能少的去覆盖区间,其实是尽可能的去覆盖点,这点容易导致大家WA

思路:

按照结束时间倒叙排列,从末端开始向前尽可能向前去包含更多的点

注意:

WA多半是你想成了包含区间段而不是点(去试一试下面的样例1,答案是4)

RE多半是你省略了不存在的情况,循环没有跳出

TLE多半是写的太暴力,优化下时间

代码:
 

#include <iostream>
#include <algorithm>
#include <cstdio>

#define     max(x, y)   x >= y ? x : y
#define     min(x, y)   x < y ? x :y

#define     INF         0x3f3f3f3f

#define     sd(x)       scanf("%d", &x)
#define     pd(x)       printf("%d\n", x)
#define     slld(x)     scanf("%lld", &x)
#define     plld(x)     printf("%lld\n", x)

#define     sdd(x, y)    scanf("%d%d", &x, &y)

using namespace std;

const int maxn = 250005;

typedef long long ll;

typedef struct node
{
    int s, e;

}node;

node a[maxn];
int n, t;

bool cmp(node s1, node s2)
{
    if (s1.e == s2.e) return s1.s <= s2.s;
    else return s1.e > s2.e;
}

int main()
{
    sdd(n, t);
    for (int i = 0; i < n; i++) sdd(a[i].s, a[i].e);

    sort(a, a + n, cmp);
//print();
    if (a[0].e < t) {cout << -1 << endl; return 0;}

    int now = a[0].s - 1;
    int ans = 1;
    int inx = 1;
    while (now >= 1)
    {
        int Min = INF;
        int sign, flag = 0;

        while (a[inx].e >= now) {
                flag = 1;
            if (a[inx].s < Min) {
                sign = inx;
                Min = a[inx].s;
            }
            inx++;
        }

        if (flag) {
            ans++;
            now = a[sign].s - 1;
        }
        else inx++;
        if (inx == n && now >= 1) {ans = -1; break;}
    }
    pd(ans);
    return 0;
}

奉献一组数据:

/*
input:
10 10
1 3
2 4
3 5
4 6
5 7
6 8
7 9
8 10
9 10
10 10

output: 4
/*

猜你喜欢

转载自blog.csdn.net/easylovecsdn/article/details/83420439
今日推荐