USACO 1.3.1 挤牛奶

1.3.1 挤牛奶

题目考查

区间合并

解题思路

我们将所有挤奶的区间按照左端点从小到大排序, 遍历所有区间.

不妨设当前连续的区间为[L, R], 遍历到的新区间为[l, r]. 此时有两种情况:
情况①: [l, r] 与 [L, R] 有交集. 则我们可以把新区间加入到老区间当中. 由于l >= L, 所以左端点无需更新, 更新右端点, 执行R = max(R, r)即可.
情况②: [l, r] 与 [L, R] 无交集. 则我们更新最长连续挤奶时间r1, 最长连续无人挤奶时间r2. 其中有: r1 = max(r1, R - L), r2 = max(r2, l - R)

题目细节

  1. 对于涉及到区间排序的问题, 需要考虑好排序的规则, 是按照左端点排序, 还是右端点.
  2. 对于涉及到区间求长度的问题, 需要考虑到是否需要 +1, -1.
  3. 对于遍历求解类问题, 我们需要考虑最后一种合法情况是否统计了. 倘若我们最后一次循环的情况也合法, 但是循环已经终止了, 导致我们少计算一种合法情况.

AC代码

#include <bits/stdc++.h>
#define rep(i, n) for (int i = 1; i <= (n); ++i)
using namespace std;
typedef long long ll;
int main()
{
	vector<pair<int, int>> v;

	int n; cin >> n;
	rep(i, n) {
		int l, r; scanf("%d %d", &l, &r);
		v.push_back({ l, r });
	}
	sort(v.begin(), v.end());

	int r1 = 0, r2 = 0; //结果
	int L = v.front().first, R = v.front().second; //题目比较毒瘤, 开始时间不是从0开始.
	for (auto& [l, r] : v) {
		if (l <= R) R = max(R, r);
		else {
			r2 = max(r2, l - R);
			r1 = max(r1, R - L);
			L = l, R = r;
		}
	}
	r1 = max(r1, R - L);

	cout << r1 << ' ' << r2 << endl;
	return 0;
}

END

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

逍遥Fau

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值