其他分享
首页 > 其他分享> > 【模板】动态凸包

【模板】动态凸包

作者:互联网

好诶,我luogu帮我成功的交了一回codeforces了

\(\textrm{CF70D - Professor's task}\)

#include <stdio.h>
#include <map>
using namespace std;
#define llt long long int
map<int,int> up, dn;
llt cross(int a,int b,int x,int y) {
	return (llt)a*y-(llt)b*x;
}
bool find_up(int x,int y) {
	map<int,int> :: iterator it1 = up.lower_bound(x);
	if(it1 == up.end()) 
		return false;
	if(it1->first == x) 
		return y <= it1->second;
	if(it1 == up.begin()) 
		return false;
	map<int,int> :: iterator it2 = it1;
	--it2;
	return cross(it1->first-it2->first,it1->second-it2->second,x-it2->first,y-it2->second) <= 0;
}
bool find_dn(int x,int y) {
	map<int,int> :: iterator it1 = dn.lower_bound(x);
	if(it1 == dn.end()) 
		return false;
	if(it1->first == x) 
		return y >= it1->second;
	if(it1 == dn.begin()) 
		return false;
	map<int,int> :: iterator it2 = it1;
	--it2;
	return cross(it1->first-it2->first,it1->second-it2->second,x-it2->first,y-it2->second) >= 0;
}
bool delete_up(map<int,int> :: iterator it) {
	if(it == up.begin()) 
		return false;
	map<int,int> :: iterator it1 = it, it2 = it;
	--it1;
	++it2;
	if(it2 == up.end()) 
		return false;
	if(cross(it->first-it1->first,it->second-it1->second,it2->first-it1->first,it2->second-it1->second) >= 0) {
		up.erase(it);
		return true;
	}
	return false;
}
bool delete_dn(map<int,int> :: iterator it) {
	if(it == dn.begin()) 
		return false;
	map<int,int> :: iterator it1 = it, it2 = it;
	--it1;
	++it2;
	if(it2 == dn.end()) 
		return false;
	if(cross(it->first-it1->first,it->second-it1->second,it2->first-it1->first,it2->second-it1->second) <= 0) {
		dn.erase(it);
		return true;
	}
	return false;
}
void insert_up(int x,int y) {
	if(find_up(x,y)) 
		return;
	up[x] = y;
	map<int,int> :: iterator it1 = up.find(x);
	map<int,int> :: iterator it2 = it1;
	if(it1 != up.begin()) {
		--it2;
		while(delete_up(it2++)) 
			--it2;
	}
	if(++it2 != up.end()) {
		while(delete_up(it2--)) 
			++it2;
	}
}
void insert_dn(int x,int y) {
	if(find_dn(x,y)) 
		return;
	dn[x] = y;
	map<int,int> :: iterator it1 = dn.find(x);
	map<int,int> :: iterator it2 = it1;
	if(it1 != dn.begin()) {
		--it2;
		while(delete_dn(it2++)) 
			--it2;
	}
	if(++it2 != dn.end()) {
		while(delete_dn(it2--)) 
			++it2;
	}
}
int n;
signed main() {
	scanf("%d",&n);
	for(int i = 1, opt, x, y;i <= n;++i) {
		scanf("%d %d %d",&opt,&x,&y);
		if(opt == 1) {
			insert_up(x,y);
			insert_dn(x,y);
		} else {
			printf("%s\n",(find_up(x,y)&&find_dn(x,y)) ? "YES" : "NO");
		}
	}
	return 0;
}

标签:dn,return,first,凸包,second,动态,it2,模板,it1
来源: https://www.cnblogs.com/bikuhiku/p/online_2D_convex_hull.html