题目传送门
一、理解与感悟
- PII记录区间。
- 排序,默认排序按左端点排序。
- 由左到右遍历每个区间,如果发生间隔,就将已经确定的区间入结果集。
- 如果发生相交或内置,则看谁管的远,就将截止点设置成谁。
- 别忘了最后一个区间也要手动添加到结果集。
二、代码模板
#include <bits/stdc++.h>
using namespace std;
typedef pair<int, int> PII;
//线段数组
vector<PII> segs;
//结果数组
vector<PII> res;
/**
* 功能:区间合并
*/
void merge() {
//如果区间为空,那还合并个头啊
if (segs.size() == 0) return;
//区间合并,必须先排序,PII排序,C++中默认是按第一个int排序的,即左边界
sort(segs.begin(), segs.end());
//初始化st=第一个区间的左边界,ed=第一个区间的右边界
int st = segs[0].first, ed = segs[0].second;
//从第二个开始进行叠加
for (int i = 1; i < segs.size(); i++)
if (ed < segs[i].first) {
//如果后面的与前面的中间存在间隔,那么需要把先面的入结果集,后面是独立的存在
res.push_back({st, ed});
//初始新的区间开始和结束
st = segs[i].first, ed = segs[i].second;
}//如果存在交集,那么取谁管的远听谁的
else ed = max(ed, segs[i].second);
//将最后一个区间记录到结果集中
res.push_back({st, ed});
}
int main() {
int n;
cin >> n;
//读入数据
for (int i = 1; i <= n; i++) {
int l, r;
cin >> l >> r;
segs.push_back({l, r});
}
//合并区间
merge();
//输出结果
cout << res.size() << endl;
return 0;
}