Interstellar Travel(凸包 hdu6325)

题目:Problem G. Interstellar Travel

官方题解:

显然坐标相同的点里只保留编号最小的点最优。

将起点到终点的路径补全为终点往下走到无穷远处,再往左走到起点正下方,再往上回到起点。任意路径中回到起点部分的代价相同,观察代价和的几何意义,就是走过部分的面积的相反数。代价和最小等价于面积最大,故一定是沿着上凸壳行走。

显然起点、终点、凸壳的拐点必须要作为降落点。对于共线的点a1,a2,...,am,若一个点ii的编号是[i,m]中最小的,那么在此处降落可以最小化字典序。

时间复杂度O(nlog n)。

#include <iostream>
#include <string>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <set>
#include <algorithm>
using namespace std;

typedef long long ll;

const int MAX = 200000 + 10;

struct node
{
	ll x, y;
	int id;
} a[MAX], p[MAX], b[MAX];

int top, n, tot;
int ans[MAX];
bool vis[MAX];

ll cross(node p0, node p1, node p2)//计算叉乘,注意p0,p1,p2的位置,这个决定了方向
{
	return (p1.x - p0.x)*(p2.y - p0.y) - (p1.y - p0.y)*(p2.x - p0.x);
}

ll dis(node a, node b)//计算距离,这个用在了当两个点在一条直线上
{
	return (a.x - b.x)*(a.x - b.x) + (a.y - b.y)*(a.y - b.y);
}

bool cmp(node p1, node p2)//去重
{
	if (p1.x == p2.x)
	{
		if (p1.y == p2.y)
			return p1.id<p2.id;
		return p1.y<p2.y;
	}
	return p1.x<p2.x;
}

bool cmp2(node p1, node p2)//极角排序
{
	ll z = cross(a[0], p1, p2);
	if (z>0 || (z == 0 && dis(a[0], p1)<dis(a[0], p2)))
		return 1;
	return 0;
}

void Graham()
{
	sort(a + 1, a + tot, cmp2);
	top = 1;
	p[0] = a[0];
	p[1] = a[1];
	for (int i = 2; i<tot; i++)
	{
		while (cross(p[top - 1], p[top], a[i])<0 && top)
			top--;
		top++;
		p[top] = a[i];
	}
}

int main()
{
	int T;
	scanf("%d", &T);
	while (T--)
	{
		memset(vis, false, sizeof(vis));
		scanf("%d", &n);
		int flag = 0;
		for (int i = 0; i<n; i++)
		{
			scanf("%lld%lld", &b[i].x, &b[i].y);
			b[i].id = i + 1;
			if (b[i].y != 0)
				flag = 1;
		}

		//去重
		sort(b + 1, b + n, cmp);
		a[0] = b[0];
		tot = 1;
		for (int i = 1; i<n; i++)
		{
			if (b[i].x == b[i - 1].x&&b[i].y == b[i - 1].y)
			{
				continue;
			}
			else
			{
				a[tot++] = b[i];
			}
		}

		//计算凸包
		Graham();

		//特判全在x轴上的情况
		if (flag == 0)
		{
			int cnt = 0;
			ans[++cnt] = p[top].id;
			for (int i = top - 1; i >= 1; i--)
			{
				if (p[i].id<ans[cnt])
					ans[++cnt] = p[i].id;
			}
			ans[++cnt] = p[0].id;
			printf("%d", ans[cnt]);
			for (int i = cnt - 1; i >= 1; i--)
			{
				printf(" %d", ans[i]);
			}
			printf("\n");
			continue;
		}

		//把共线但没包含在凸包p[]中的点加进来
		//这些点只会出现在p[0]和p[top]的连线上
		int now = top;
		int nowid = p[top].id;
		for (int i = tot - 1; i>0; i--)
		{
			ll z = cross(p[now], p[0], a[i]);
			if (z == 0 && a[i].id != nowid) {
				p[++top] = a[i];
			}
		}

		//记录拐点
		sort(p, p + top + 1, cmp);
		for (int i = 1; i < top; i++)
		{
			if (cross(p[i - 1], p[i], p[i + 1]) != 0)
				vis[i] = true;
		}


		int cnt = 0;
		ans[++cnt] = p[top].id;
		for (int i = top - 1; i >= 0; i--)
		{
			if (vis[i] == true)
			{
				ans[++cnt] = p[i].id;
				continue;
			}
			if (p[i].id < ans[cnt])
				ans[++cnt] = p[i].id;
		}

		printf("%d", ans[cnt]);
		for (int i = cnt - 1; i >= 1; i--)
		{
			printf(" %d", ans[i]);
		}
		printf("\n");
	}
	return 0;
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
How should we use data to help us analyse our beliefs? This book is concerned with the subjectivist analysis of uncertainty, and develops methods that combine prior judgements with information derived from relevant data. Whenever we move from broadly data-focused questions, such as ‘Does this data set suggest that a certain medical treatment is likely to be effective?’, to broadly decision-motivated questions, such as ‘Are we sufficiently confident, given all that we know about this treatment, to recommend its widespread use?’, then we must make such a synthesis of data with more generalized forms of information. Because we may find this hard to achieve, we need some methodology to help us. This methodology should be clear, helpful, logically well founded and tractable. The Bayesian approach to statistics is the natural methodology for this purpose. This approach treats all uncertainties within a common probabilistic framework, combining the different sources of information using the rules of probability. This approach has a sound logical foundation and a well-developed methodology and is popular and successful in many areas of application. However, in large-scale applications, the Bayesian approach can easily become the victim of its own ambition. Representing all uncertainties in probabilistic form is a daunting task for complicated problems. This is partly because of the intrinsic difficulties in judging the value of each relevant source of knowledge. However, in large part, the task is difficult because the Bayesian approach requires us to specify our uncertainties to an extreme level of detail. In practice, it is usually beyond our ability to make meaningful specifications for our joint probability distributions for multiple outcomes. If we do wish to follow a broadly Bayesian path, then we must either choose to make specifications that do not correspond to our actual uncertainties or be more modest about our ability to render our beliefs in probabilistic form. If the data are plentiful and unambiguous in their message or if the problem is not sufficiently important to merit careful analysis, then little harm is done by somewhat misrepresenting our beliefs. However, when the issue is important and data are less plentiful, then we must be more careful and honest. When we cannot make full belief specifications, we require alternative methods that respect the limitations on our abilities to specify meaningful beliefs and allow us to conduct partial analyses strictly in terms of the actual limited aspects of our beliefs that we are able to specify.

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值