抓拍

  • 果然还是分类讨论有疏漏:未考虑到两段移动区间“迎头相撞”的情况,思维要更加缜密
  • 更简洁的做法是,考察周长关于时间的函数,通过三分法找极小值点
  • 两个凹函数的和仍是凹函数,两个凸函数的和仍是凸函数(定义法证明)
  • abs和llabs都可以将long long类型的数取绝对值,其区别在于,若令x=-2147483648,llabs可以正常得到2147483648的结果,而abs不能
点击查看代码
#include <bits/stdc++.h>
using namespace std;
vector<int> x,y;
vector<int>a[5];
int q[205],n;
const int dx[]={0,1,-1,0,0};
const int dy[]={0,0,0,-1,1};
struct t1
{
	long long x,y,opt;
}t[200005];
long long calc(long long T)
{
	if(T<0)
	{
		T=-T;
	}
	long long maxx=LLONG_MIN,minx=LLONG_MAX,maxy=LLONG_MIN,miny=LLONG_MAX;
	for(int i=1;i<=n;i++)
	{
		t[i].x+=(dx[t[i].opt]*T);
		t[i].y+=(dy[t[i].opt]*T);
		maxx=max(maxx,t[i].x);
		minx=min(minx,t[i].x);
		maxy=max(maxy,t[i].y);
		miny=min(miny,t[i].y);
		t[i].x-=(dx[t[i].opt]*T);
		t[i].y-=(dy[t[i].opt]*T);
	}
	return 2*(maxx-minx+maxy-miny);
}
int main()
{
	q['E']=1;q['W']=2;q['S']=3;q['N']=4;
	ios::sync_with_stdio(false);
	cin.tie(0);
	cin>>n;
	for(int i=1;i<=n;i++)
	{
		int u,v;
		char c;
		cin>>u>>v>>c;
		t[i].x=u;
		t[i].y=v;
		t[i].opt=q[c];
		if(q[c]<=2)
		{
			a[q[c]].push_back(u);
		}
		else
		{
			a[q[c]].push_back(v);
		}
		if(c=='E'||c=='W')
		{
			y.push_back(v);
		}
		else
		{
			x.push_back(u);
		}
	} 
	sort(x.begin(),x.end());
	sort(y.begin(),y.end());
	for(int i=1;i<=4;i++)
	{
		sort(a[i].begin(),a[i].end());
	}
	long long ans=calc(0);
	if(x.size()!=0)
	{
		int lx=*x.begin(),rx=*(--x.end());
		for(int i=1;i<=2;i++)
		{
			if(a[i].size()>0)
			{
				ans=min(ans,calc(lx-*(a[i].begin())));
				ans=min(ans,calc(rx-*(a[i].begin())));
				ans=min(ans,calc(lx-*(--a[i].end())));
				ans=min(ans,calc(rx-*(--a[i].end())));
			}
		}
	}
	if(a[1].size()>0&&a[2].size()>0)
	{
		int lx=*a[1].begin(),rx=*(--a[1].end());
		ans=min(ans,calc((lx-*(a[2].begin()))/2));
		ans=min(ans,calc((rx-*(a[2].begin()))/2));
		ans=min(ans,calc((lx-*(--a[2].end()))/2));
		ans=min(ans,calc((rx-*(--a[2].end()))/2));
		ans=min(ans,calc((lx-*(a[2].begin()))/2+1));
		ans=min(ans,calc((rx-*(a[2].begin()))/2+1));
		ans=min(ans,calc((lx-*(--a[2].end()))/2+1));
		ans=min(ans,calc((rx-*(--a[2].end()))/2+1));
	}
	if(y.size()!=0)
	{
		int ly=*y.begin(),ry=*(--y.end());
		for(int i=3;i<=4;i++)
		{
			if(a[i].size()>0)
			{
				ans=min(ans,calc(ly-*(a[i].begin())));
				ans=min(ans,calc(ry-*(a[i].begin())));
				ans=min(ans,calc(ly-*(--a[i].end())));
				ans=min(ans,calc(ry-*(--a[i].end())));
			}
		}
	}
	if(a[3].size()>0&&a[4].size()>0)
	{
		int lx=*a[3].begin(),rx=*(--a[3].end());
		ans=min(ans,calc((lx-*(a[4].begin()))/2));
		ans=min(ans,calc((rx-*(a[4].begin()))/2));
		ans=min(ans,calc((lx-*(--a[4].end()))/2));
		ans=min(ans,calc((rx-*(--a[4].end()))/2));
		ans=min(ans,calc((lx-*(a[4].begin()))/2+1));
		ans=min(ans,calc((rx-*(a[4].begin()))/2+1));
		ans=min(ans,calc((lx-*(--a[4].end()))/2+1));
		ans=min(ans,calc((rx-*(--a[4].end()))/2+1));
	}
	cout<<ans<<endl;
	return 0;
}
posted @ 2024-07-27 12:35  D06  阅读(2)  评论(0编辑  收藏  举报