hrbust 哈理工oj 1729 Finding the Way【计算几何】

Finding the Way
Time Limit: 1000 MSMemory Limit: 32768 K
Total Submit: 87(26 users)Total Accepted: 38(26 users)Rating: Special Judge: No
Description

There suppose to be several mines on a plain numbered from 1 to n. Now a robot want to test them one by one from No.1 to No.n.

The robot start from the coordinate(0,0), and the direction is to the first point.The first point will never be(0,0).

If the robot turns left, output"left".

If it turns right, output"right". 

If it goes front, output"toward". 

If it goes back, output"backward". 

If it stands there, output "stand".


The robot is so smart that it will turn by the minimum angle.

Input

There are multiple test cases. The first line is an integer T indicating the number of test cases.

The first line of each test case is positive integer n, standing for the number of mines.

Then n lines following, each line shows the coordinate of the mine(xi, yi).( 2 <= n <= 100, 0 <= xi, yi <= 10000 )

Output

For each test case, output n-1 lines, each line is the direction to the next mine by the minimum angle.

Output a blank line after each test case.

Sample Input
3
4
20 3
40 6
57 94
77 28
4
14 96
26 12
52 24
84 5
4
95 27
95 27
72 26
36 13
Sample Output
toward
left
right

right
left
right

stand
left
left
Source
哈理工2013春季校赛 - 网络预选赛
Author
黄李龙@HRBUST
/*

WA无数发,最后还是看大牛代码过的。表示计算几何也有很多坑点。。。。。

*/

这个题AC有两个重要的点:

1、判断左右拐、

2、判断不动,前进和后退、

第一个点很好控制,直接叉乘就可以了。

第二个算是这个题的难点,坑点也是在这里,

1、首先我们知道,如果站下就是在叉乘为0的同时,p2==p3。

2、如果是p1==p2,那么表示上一次是站下没有动,那么这次无论向什么方向走,都叫向前走。

3、对于判断共线的两个有向向量的方向,三个点,求出两个x该变量,求出两个y改变量,如果x的改变量方向相同,并且y的改变量方向相同,我们就能知道这是在向前走,相反就是反向走。

(几何题可能口述比较乱,对应代码慢慢理解)

那么最终得到这样的代码:

#include<stdio.h>
#include<string.h>
using namespace std;
struct Point
{
	int x,y;
};
int chacheng(Point p1, Point p2, Point p3)
{
	return (p2.x-p1.x)*(p3.y-p1.y)-(p3.x-p1.x)*(p2.y-p1.y);
}
int judge(Point p1, Point p2, Point p3)
{
	int disx1=p2.x-p1.x;
	int disy1=p2.y-p1.y;
	int disx2=p3.x-p2.x;
	int disy2=p3.y-p2.y;
	if(disx1==disy1&&disx1==0)return 1;//原地之后,之后叫做向前走、
	if(disx1!=0&&disy1!=0&&disx2==disy2&&disx2==0)return 2;//原地走
	if(disx1*disx2>0&&disy1*disy2>0)return 3;//qian
	if(disx1*disx2<0&&disy1*disy2<0)return 4;//hou
}
int main()
{
    int t;
    scanf("%d",&t);
    while(t--)
    {
        Point p1,p2,p3;
        int n;
        scanf("%d",&n);
        p1.x=0;
        p1.y=0;
        scanf("%d%d",&p2.x,&p2.y);
        for(int i=2;i<=n;i++)
        {
            scanf("%d%d",&p3.x,&p3.y);
            int a=chacheng(p1,p2,p3);
            int b=judge(p1,p2,p3);
            if(a>0)
            {
                printf("left\n");
            }
            if(a<0)叉乘小于0,说明p1p2是由p1p3逆时针旋转得到的,那么p3就是在p1p2右边、
            {
                printf("right\n");
            }
            if(a==0)
            {
                if(b==1)
                {
                    printf("toward\n");
                }
                if(b==2)
                {
                    printf("stand\n");
                }
                if(b==3)
                {
                    printf("toward\n");
                }
                if(b==4)
                {
                    printf("backward\n");
                }
            }
            if(p2.x!=p3.x&&p2.y!=p3.y)
            {
                p1=p2;
                p2=p3;
            }
        }
        printf("\n");
    }
}






评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值