第一眼看到这个题我便想到这题得用结构体存和排序。后面写的时候感觉和以前做过的贪心的题有点像,我就以为这题很简单,然后wrong answer了好久。
结构体的存储使得这个区间便于操作,sort函数正好也可以对结构体排序
sort对于结构体的排序有两种方法,一种是重载小于号,另一种是写一个比较函数,我一般使用第二种,比较好写一些,不过两种方法我都写了出来可以参考一下选择适合自己的一种方法。
这道题大概的解题思路是,我们先使用排序使得每一个区间的左端点是从小到大排序的,这样可以保证我们每一个区间的左端点尽可能的小,尽可能的会在上一个右端点的范围内。接下来就是比较当前区间的右端点和下一个区间的左端点的关系,如果是包含(下一个区间的左端点小于等于上一个区间的右端点)的关系,那么我们比较当前的右端点个下一个区间的右端点大小,如果新的端点大的话,我们便更新端点的值。如果不包含我们直接退出,返回”no“。我便是卡在了这一步,当时的我想不明白为什么要更新这个端点,最后一个区间的右端点不就是最大的端点值吗,我就转不过来了,就一直wrong answer。后来我自己写输入数据的时候发现了,这是错误的比如
4
1 9
2 3
3 4
4 6
这组数据的结果应该是1 9,但是如果按我错误的想法做,这题的结果就是1 6便错误了。
这道题本身并不难没关键是我们是否能考虑清楚每个细节和如何处理好这些细节!!!
比较函数的写法
#include<iostream>
#include<algorithm>
using namespace std;
int n;
struct f
{
int l;
int r;
}s[50010];
bool cmp(f a, f b)
{
return a.l < b.l;
}
int main()
{
cin >> n;
for (int i = 0; i < n; i++)
cin >> s[i].l >> s[i].r;
sort(s, s + n, cmp);
int min = s[0].l, max = s[0].r;
for (int i = 1; i < n; i++)
{
if (s[i].l <= max)
{
if (s[i].r > max)//非常关键!!!!!一定要理解为什么最后一组数据的r未必是最大的数
//当最后一个数的开端最大时,他结束的值未必是最大的
max = s[i].r;
}
else
{
puts("no");
return 0;
}
}
cout << min << " " << max << endl;
return 0;
}
重载小于号的写法
#include<iostream>
#include<algorithm>
using namespace std;
int n;
struct f
{
int l;
int r;
bool operator <(const f& t)
{
return l < t.l;
}
}s[50010];
bool cmp(f a, f b)
{
return a.l < b.l;
}
int main()
{
cin >> n;
for (int i = 0; i < n; i++)
cin >> s[i].l >> s[i].r;
sort(s, s + n);
int min = s[0].l, max = s[0].r;
for (int i = 1; i < n; i++)
{
if (s[i].l <= max)
{
if (s[i].r > max)//非常关键!!!!!一定要理解为什么最后一组数据的r未必是最大的数
//当最后一个数的开端最大时,他结束的值未必是最大的
max = s[i].r;
}
else
{
puts("no");
return 0;
}
}
cout << min << " " << max << endl;
return 0;
}