求凸包或者闭包的顺序
原创
©著作权归作者所有:来自51CTO博客作者wx634fafb167087的原创作品,请联系作者获取转载授权,否则将追究法律责任
已知一个多边形N有点A,B,C,D,E,F,G,H组成,切多边形的凹凸性不确定,如何判断多边形的方向呢。
如果多边形为凸多边形,则判断方法很简单,只需要取出顺序的三个点,如:A,B,C 三点,计算向量AB,BC的叉乘,得到的结果如果大于0,则表示C点在AB的左侧,多边形的顶点是顺时针序,这样也能判断该凸多边形为顺时针序,反之,则为逆时针序。
比如选择了C点作为顶点来判断,BC,CD的叉乘结果
此时,我们就需要选择好用来判断的点。
解决方法为:选择多边形的凸点进行判断,选择该凸点的前一个和后一个点按上述方法判断,这样判断结果依然正确。
叉乘:矢量P(X1,Y1),矢量Q(X2,Y2),则PxQ=X1*Y2-X2*Y1
若PxQ>0,则P在Q的顺时针方向
若PxQ<0,则P在Q的逆时针方向
若PxQ=0,则P和Q共线,但可能同向也可能反向
题目链接:https://www.nowcoder.com/acm/contest/110/B
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
#include<vector>
#include<queue>
#define ls 2*rt
#define rs 2*rt+1
#define lson ls,L,mid
#define rson rs,mid+1,R
#define ll long long
using namespace std;
typedef pair<int,int> pii;
const ll inf = 0x3f3f3f3f;
/*void dis(int a[], int n){
printf("总数为%d个\n",n);
for(int i = 0; i < n; i++) cout<<a[i]<<", ";
cout<<endl<<"------------------"<<endl;
}*/
const int mx = 0;
int x[100],y[100];
int main(){
//int T=10;
int n;
scanf("%d",&n);
int max_x = - 2000,max_y=-2000,id_x,id_y;
for(int i = 0; i < n; i++){
scanf("%d%d",x+i,y+i);
if(x[i] > max_x){
max_x = x[i];
id_x = i;
}
if(y[i] > max_y){
max_y = y[i];
id_y = i;
}
}
// int f = (x[2]-x[1])*(y[3]-y[2])-(y[2]-y[1])*(x[3]-x[2]);
int f= (x[id_x]-x[id_x-1+n%n])*(y[id_x+1%n]-y[id_x]) - (x[id_x+1%n]-x[id_x])*(y[id_x]-y[id_x-1+n%n]);
if(f== 0){
f= (x[id_y]-x[id_y-1+n%n])*(y[id_y+1%n]-y[id_y]) - (x[id_y+1%n]-x[id_y])*(y[id_y]-y[id_y-1+n%n]);
}
if(f < 0)
puts("clockwise");
else{
puts("counterclockwise");
}
return 0;
}