Hunter’s Apprentice

问题 H: Hunter’s Apprentice

时间限制: 1 Sec  内存限制: 128 MB
提交: 385  解决: 65
[提交] [状态] [命题人:admin]

题目描述

When you were five years old, you watched in horror as a spiked devil murdered your parents. You would have died too, except you were saved by Rose, a passing demon hunter. She ended up adopting you and training you as her apprentice.
Rose’s current quarry is a clock devil which has been wreaking havoc on the otherwise quiet and unassuming town of Innsmouth. It comes out each night to damage goods, deface signs, and kill anyone foolish enough to wander around too late. The clock devil has offed the last demon hunter after it; due to its time-warping powers, it is incredibly agile and fares well in straight-up fights.
The two of you have spent weeks searching through dusty tomes for a way to defeat this evil. Eventually, you stumbled upon a relevant passage. It detailed how a priest managed to ensnare a clock devil by constructing a trap from silver, lavender, pewter, and clockwork. The finished trap contained several pieces, which must be placed one-by-one in the shape of a particular polygon, in counter-clockwise order. The book stated that the counter-clockwise order was important to counter the clock devil’s ability to speed its own time up, and that a clockwise order would only serve to enhance its speed.
It was your responsibility to build and deploy the trap, while Rose prepared for the ensuing fight. You carefully reconstruct each piece as well as you can from the book. Unfortunately, things did not go as planned that night. Before you can finish preparing the trap, the clock devil finds the two of you. Rose tries to fight the devil, but is losing quickly. However, she is buying you the time to finish the trap. You quickly walk around them in the shape of the polygon, placing each piece in the correct position. You hurriedly activate the trap as Rose is knocked out. Just then, you remember the book’s warning. What should you do next?

 

输入

The first line of input contains a single integer T (1 ≤ T ≤ 100), the number of test cases. The first line of each test case contains a single integer n (3 ≤ n ≤ 20), the number of pieces in the trap. Each of the next n lines contains two integers xi and yi (|xi |, |yi | ≤ 100), denoting the x and y coordinates of where the ith piece was placed. It is guaranteed that the polygon is simple; edges only intersect at vertices, exactly two edges meet at each vertex, and all vertices are distinct.

 

输出

For each test case, output a single line containing either fight if the trap was made correctly or run if the trap was made incorrectly.

 

样例输入

复制样例数据

2
3
0 0
1 0
0 1
3
0 0
0 1
1 0

样例输出

fight
run

 

提示

In the first case, you went around the polygon in the correct direction, so it is safe to fight the clock devil
and try to save Rose.
In the second case, you messed up, and it is time to start running. Sorry Rose!

思路:之前我记得做过一个判断某个点的位置是不是在多边形内的题目,然后还保存了一份模板,没想到这个题居然用上了,我们可以发现这样的一个事实:那就是如果多边形是顺时针的话,紧挨着每条边右侧的点就会在多边形内,相反,如果紧挨着每条边右侧的点都不在多边形内,那么多边形就是逆时针。最后就是套用模板,用我们找到的紧挨着每条边右侧的点去判断是不是在多边形内就可以出结果

#include<cstdio>
#include<iostream>
#include<string.h>
#include<set>
#include<string>
#include<math.h>
#include<queue>
#include<stack>
#include<algorithm>
#define sc(a) scanf("%d",&a)
#define scl(a) scanf("%lld",&a)
#define mem(a) memset(a,0,sizeof(a));
#define pr(a) printf("%d\n",a);
#define prl(a) printf("%lld\n",a);
typedef long long int LL;
using namespace std;
const double dis = 0.00000000001;
const int N = 30;
char ch[N][N];
double x[N];
double y[N];
/* 函数功能: 判断点(x, y)是否在有ploy_sides个顶点的多边形内 */
/* 参数: poly_sides    测试多边形的顶点数
**    poly_x    测试多边形的各个顶点的X轴坐标
**    poly_y    测试多边形的各个顶点的Y轴坐标
**    x    测试点的X轴坐标
**    Y 测试点的Y轴坐标 */
/* 返回值: 返回0 表示不在多边形内部,返回1 表示在多边形内部 */
/* 说明: 在多边形各边上的点默认不在多边形内部 */
int inOrNot(int poly_sides, double *poly_X, double *poly_Y, double x, double y)//判断x,y是不是在多边形内,poly_sides:边的个数,poly_x,poly_y为位置数组
{
	int i, j;
	j = poly_sides - 1;
	int res = 0;
	for (i = 0; i < poly_sides; i++)
	{
		//对每一条边进行遍历,该边的两个端点,有一个必须在待检测点(x,y)的左边,且两个点中,有一个点的y左边比p.y小,另一个点的y比p.y大。
		if ((poly_Y[i] < y && poly_Y[j] >= y || poly_Y[j] < y && poly_Y[i] >= y) && (poly_X[i] <= x || poly_X[j] <= x))
		{
			//用水平的直线与该边相交,求交点的x坐标。
			res ^= ((poly_X[i] + (y - poly_Y[i]) / (poly_Y[j] - poly_Y[i])*(poly_X[j] - poly_X[i])) < x);
		}
		j = i;
	}
	return res;
}


int main() {

	int t;
	sc(t);
	while (t--) {
		mem(ch);
		mem(x);
		mem(y);
		int n;
		sc(n);
		for (int i = 0; i < n; i++) {
			cin >> x[i] >> y[i];
		}

 		bool flag = false;
		for (int i = 1; i < n; i++) {
			double x2 = x[i];
			double y2 = y[i];
			double x1 = x[i - 1];
			double y1 = y[i - 1];
			double cenx;
			double ceny;
			double aimx, aimy;
			ceny = (y1 + y2) / 2;//cenx,ceny分别为每条边的中点的坐标
			cenx = (x1 + x2) / 2;
			//接下来判断每条边的朝向
			if (x1 ==x2) {
				cenx = (x1 + x2) / 2;
				ceny = (y1 + y2) / 2;
				if (y2 > y1) {//边竖直向上
					cenx += dis;//那么右侧的点为x加上一丢丢距离
				}
				else {//边竖直向下
					cenx -= dis; //那么右侧的点为x减去一丢丢距离
				}

			}

			else if (y1 == y2) {

				if (x2 > x1) {//边水平向右
					ceny -=dis;//右侧点在ceny的下侧
				}
				else {//边水平向左
					ceny += dis;//右侧点在ceny的上测
				}
			}

			else {
				if (x2 - x1 > 0) {
					if (y2 - y1 > 0) {//边朝右上方
						cenx += dis;//将右侧点的坐标定位到右下方
						ceny -= dis;
					}
					else {//边朝右下方
						cenx -= dis;//将右侧点的坐标定位到左下方
						ceny -=dis;
					}

				}
				else {
					if (y2 - y1 > 0) {//边朝左上方
						cenx += dis;//将右侧点的坐标定位到右上方
						ceny += dis;
					}
					else {//边朝左下方
						cenx -= dis;//将右侧点的坐标定位到左上方
						ceny += dis;
					}

				}


			}
			
			if (inOrNot(n, x, y, cenx, ceny) == 1) {//最后保险起见判断每条边右侧的点是否在多边形内,只要有一个在,就是顺时针
				flag = true;
				break;

			}
			

		}
		if (flag) {
			printf("run\n");
		}
		else {
			printf("fight\n");
		}

	}

	return 0;
}

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值