lanqiao OJ 111 区间位移

1.区间移位 - 蓝桥云课 (lanqiao.cn)

二分+贪心,  二分和贪心总是同时出现嘛  , 二分倒是简单,贪心总是很难证明也很难想到,

参考一下这两个博客

蓝桥杯历年真题——区间位移——JAVA 详解_蓝桥杯 区间位移-CSDN博客

蓝桥杯国赛第八届c++ A组 区间移位_数轴上有n个闭区间d1,…,dn。其中区间di用一对整数[ai, bi]来描述,满足ai < bi。-CSDN博客

#include<iostream>
#include<cstring>
#include<algorithm>
#include<vector>
using namespace std ;
const int N = 1e4 + 10 ;
struct node{
	int a,b ;
	node(int aa, int bb){
		a = aa, b = bb ;
	}
};
bool cmp(node q,node w){
	return q.b < w.b ;
}
int n ;
vector<node> q ;
bool check(int mid){//先找出一个mid值
	int pos = 0 ;
	vector<node> temp(q) ;//复制原来数组,因为我们后边会对数组中的某些个点进行清楚,为了不影响下一次二分,我们用这个复制数组来操作
	while(1){
		bool flag = false ;//如果循环结束后还是false 说明区间有了不能补上的空点,如果还没有到达最后的点20000直接返回0 ;
		for(int i = 0 ; i < temp.size() ; i++ ){//从头到尾遍历每一个区间,如果又符合条件的就把这个区间放上去,对pos值进行修改
			int na = temp[i].a , nb = temp[i].b ;
			int len = nb - na ;//当前区间左端,右端,长度
			if(na - mid <= pos && nb + mid >= pos){//当前pos 在区间内,或者在移动后区间内,这样的区间符合条件
				flag = 1 ;//找到一个符合条件的区间了,进行下一次循环
				//两种情况的pos的值的更新
                if(na + mid >= pos) pos += len ; // 1.最左端移动小于等于mid就可以到达pos,那pos直接加上区间长度len
				else pos = nb + mid ;//2.最左端移动了mid了,但是还不到不了pos,就只能让去掉重复的那一块了,
				temp.erase(temp.begin()+i) ;//避免区间重复判断
				break; //找到一个符合的了,重新开始从头找
			}
		}
		if(pos>=20000 || !flag) break ;
	}
	return pos >= 20000 ;
}
int main(){
	cin >> n ;
	for(int i = 0 ; i < n ;i  ++){
		int a, b ;
		cin >> a >> b ; a*=2,b*=2 ;
		q.push_back(node(a,b)) ;
	}
	sort(q.begin(),q.end(),cmp) ; // 这是vector 的排序方法,一定要记住
	int l = 0 , r = N ;
	while(l<r){//二分
		int mid = l + r  >> 1 ;
		if(check(mid)) r = mid ;
		else l = mid + 1 ;
	}
	cout << ((double)r ) / 2 << endl ;//因为刚开是把数组都扩展了一倍,所以数组先都乘2
}

  • 3
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值