列表

详情


NC214894. Octasection

描述

At the Namomo Camp, a cute volunteer celebrates her birthday. Wowo buys her a huge cake. (The cake is so big that it has a 3D coordinate system inside.) There are cuboid shaped pieces of chocolates in the cake. The -th () chocolate consists of all points such that . are arrays of integers. Chocolates may overlap or touch each other.

The volunteer wants to distribute the cake to the campers of the Namomo Camp. To show off his knife skill, Wowo decides to cut the cake into pieces by exactly cuts such that:

1. The first cut is a plane whose equation is for some integer decided by Wowo.
2. The second cut is a plane whose equation is for some integer decided by Wowo.
3. The third cut is a plane whose equation is for some integer decided by Wowo.
4. Each chocolate is touched by at least one cut (i.e. each cuboid has a nonempty intersection with at least one plane).

Decide whether Wowo can cut the cake under the rules. If the answer is yes, output any possible solution.

输入描述

The first line contains a single integer  ().

The -th line of the next lines contains integers (, , , ).

输出描述

If Wowo can cut the cake under the rules, the first line of the output should contain "YES" and the second line should contain  integers ,  and  (). If Wowo cannot cut the cake under the rules, output only one line containing "NO".

示例1

输入:

3
0 1 0 1 0 1
10 11 10 11 10 11
999999999 1000000000 999999999 1000000000 999999999 1000000000

输出:

YES
0 10 999999999

示例2

输入:

4
0 1 0 1 0 1
999999999 1000000000 0 1 0 1
0 1 999999999 1000000000 0 1
0 1 0 1 999999999 1000000000

输出:

YES
0 0 0

原站题解

上次编辑到这里,代码来自缓存 点击恢复默认模板

C++(clang++11) 解法, 执行用时: 544ms, 内存消耗: 104788K, 提交时间: 2021-01-24 11:23:35

#include<bits/stdc++.h>
using namespace std;
const int N=800005;
struct sq{int x1,x2,y1,y2;};
struct node
{
	int mn1,mx1,mn2,mx2,mx,t1,t2;
	node(){}
};
int n,a[N][6],sx,sy,sz,st[N],tp;
vector<int>v[3];
vector<sq>t[N];
node s[N],tr[N];
node operator+(node a,node b)
{
	node c;
	c.mn1=min(a.mn1,b.mn1);
	c.mx1=max(a.mx1,b.mx1);
	c.mn2=min(a.mn2,b.mn2);
	c.mx2=max(a.mx2,b.mx2);
	c.mx=max(a.mx,b.mx);
	c.t1=c.t2=0;
	return c;
}
void build(int k,int l,int r)
{
	tr[k].mn1=tr[k].mx1=0;
	tr[k].mn2=tr[k].mx2=tr[k].mx=sy+1;
	tr[k].t1=tr[k].t2=0;
	if(l==r)
		return;
	int mid=l+r>>1;
	build(k<<1,l,mid);
	build(k<<1|1,mid+1,r);
}
void add(int k,int l,int r,int a,int b,sq x)
{
	if(a>b)
		return;
	if(l==a&&r==b)
	{
		t[k].push_back(x);
		return;
	}
	int mid=l+r>>1;
	if(b<=mid) add(k<<1,l,mid,a,b,x);
	else if(a>mid) add(k<<1|1,mid+1,r,a,b,x);
	else add(k<<1,l,mid,a,mid,x),add(k<<1|1,mid+1,r,mid+1,b,x);
}
void rm(int k)
{
	tp++;
	st[tp]=k;
	s[tp]=tr[k];
}
void undo(int d)
{
	while(tp!=d)
	{
		tr[st[tp]]=s[tp];
		tp--;
	}
}
void upd1(int k,int v)
{
	rm(k);
	tr[k].mn1=tr[k].mx1=tr[k].t1=v;
	tr[k].mx=tr[k].mx2-v;
}
void upd2(int k,int v)
{
	rm(k);
	tr[k].mn2=tr[k].mx2=tr[k].t2=v;
	tr[k].mx=v-tr[k].mn1;
}
void pd(int k)
{
	if(tr[k].t1==0&&tr[k].t2==0)
		return;
	rm(k);
	if(tr[k].t1)
	{
		upd1(k<<1,tr[k].t1);
		upd1(k<<1|1,tr[k].t1);
		tr[k].t1=0;
	}	
	if(tr[k].t2)
	{
		upd2(k<<1,tr[k].t2);
		upd2(k<<1|1,tr[k].t2);
		tr[k].t2=0;
	}
}
void update1(int k,int l,int r,int a,int b,int v)
{
	if(a>b)
		return;
	if(tr[k].mn1>=v)
		return;
	if(l==a&&r==b&&tr[k].mx1<=v)
	{
		upd1(k,v);
		return;
	}
	pd(k);
	int mid=l+r>>1;
	if(b<=mid) update1(k<<1,l,mid,a,b,v);
	else if(a>mid) update1(k<<1|1,mid+1,r,a,b,v);
	else update1(k<<1,l,mid,a,mid,v),update1(k<<1|1,mid+1,r,mid+1,b,v);
	rm(k);
	tr[k]=tr[k<<1]+tr[k<<1|1];
}
void update2(int k,int l,int r,int a,int b,int v)
{
	if(a>b)
		return;
	if(tr[k].mx2<=v)
		return;
	if(l==a&&r==b&&tr[k].mn2>=v)
	{
		upd2(k,v);
		return;
	}
	pd(k);
	int mid=l+r>>1;
	if(b<=mid) update2(k<<1,l,mid,a,b,v);
	else if(a>mid) update2(k<<1|1,mid+1,r,a,b,v);
	else update2(k<<1,l,mid,a,mid,v),update2(k<<1|1,mid+1,r,mid+1,b,v);
	rm(k);
	tr[k]=tr[k<<1]+tr[k<<1|1];
}
void query(int k,int l,int r,int z)
{
	if(l==r)
	{
		int x=l,y=tr[k].mn1;
		printf("YES\n%d %d %d\n",v[0][x-1],v[1][max(y-1,0)],v[2][z-1]);
		exit(0);
	}
	pd(k);
	int mid=l+r>>1;
	if(tr[k<<1].mx>=0) query(k<<1,l,mid,z);
	else query(k<<1|1,mid+1,r,z);
}
void sol(int k,int l,int r)
{
	int d=tp;
	for(auto i:t[k])
	{
		update1(1,1,sx,1,i.x1-1,i.y1);
		update1(1,1,sx,i.x2+1,sx,i.y1);
		update2(1,1,sx,1,i.x1-1,i.y2);
		update2(1,1,sx,i.x2+1,sx,i.y2);
	}
	if(l==r)
	{
		if(tr[1].mx>=0)
			query(1,1,sx,l);
		undo(d);
		return;
	}
	int mid=l+r>>1;
	sol(k<<1,l,mid);
	sol(k<<1|1,mid+1,r);
	undo(d);
}
int main()
{
	scanf("%d",&n);
	for(int i=1;i<=n;i++)
	{
		for(int j=0;j<6;j++)
		{
			scanf("%d",&a[i][j]);
			v[j/2].push_back(a[i][j]+(j&1));
		}
	}
	for(int j=0;j<3;j++)
	{
		sort(v[j].begin(),v[j].end());
		v[j].erase(unique(v[j].begin(),v[j].end()),v[j].end());
	}
	sx=v[0].size()-1,sy=v[1].size()-1,sz=v[2].size()-1;
	for(int i=1;i<=n;i++)
	{
		for(int j=0;j<6;j++)
		{
			a[i][j]=lower_bound(v[j/2].begin(),v[j/2].end(),a[i][j]+(j&1))-v[j/2].begin()+1;
			if(j&1)
				a[i][j]--;
		}
		add(1,1,sz,1,a[i][4]-1,{a[i][0],a[i][1],a[i][2],a[i][3]});
		add(1,1,sz,a[i][5]+1,sz,{a[i][0],a[i][1],a[i][2],a[i][3]});
	}
	build(1,1,sx);
	sol(1,1,sz);
	puts("NO");
	return 0;
}

上一题