计算几何模板

来源:互联网 发布:qq邮箱申请淘宝账号 编辑:程序博客网 时间:2024/06/01 19:45

先开帖..以后慢慢完善.....

首先是struct point.自定义"点"类.用来存向量.

struct point{db x; db y;point(db a=0,db b=0):x(a),y(b){}//赋值point operator=(point f){ x=f.x; y=f.y; return *this; }//向量和point operator+(point f){ return point(x+f.x,y+f.y); }//向量差point operator-(point f){ return point(x-f.x,y-f.y); }//从本顶点出发,指向另一个点的向量point operator()(point f){ return f-(*this); }//数乘point operator*(int f) { return point(x*f,y*f); }//叉积db operator*(point f){ return x*f.y - y*f.x; }//点积db operator/(point f){ return x*f.x + y*f.y; }//向量的模db length(){ return sqrt(x*x+y*y); }//判断是否相等bool operator==(point f){ return x==f.x && y==f.y; }//判断本向量在另一个向量的逆时针方向bool operator<<(point f) { return (*this)*f<0; }//判断本向量在另一个向量的逆时针方向或同向 bool operator<<=(point f) { return (*this)*f<=0; }//判断本向量在另一个向量的顺时针方向bool operator>>(point f) { return (*this)*f>0; }//判断本向量在另一个向量的顺时针方向或同向 bool operator>>=(point f) { return (*this)*f>=0; }//按照y为第一关键字,x为第二关键字进行比较bool operator<(const point f) const{ return y<f.y || (y==f.y && x<f.x); }};



接着是凸包.....

发现凸包竟敢如此好写.....

void GRAHAM(){sort(a,a+n);st=0;for(int i=0;i<n;i++){while( st>1 &&( stk[st-2](stk[st-1])>>stk[st-1](a[i])) ) st--;stk[st++]=a[i];}int p=st;for(int i=n-2;i>=0;i--){while( st>p && ( stk[st-2](stk[st-1])>>stk[st-1](a[i])) ) st--;stk[st++]=a[i];}}
注意如果只想要凸包的顶点,那么程序中的>>(判断顺时针方向)要改成>>=(判断顺时针方向或同向)

接着是旋转卡壳

int res=0;int p=2;for(int i=1;i<st;i++) //segment:stk[i-1],stk[i] vertix: stk[p].{while( p!=st && area(stk[i-1], stk[i], stk[p+1]) >area(stk[i-1], stk[i], stk[p]))p++;if(p==st) break;res=max(res,stk[i-1](stk[p]).dist2());res=max(res,stk[i](stk[p]).dist2());}

程序求的是凸包上最远点对.求别的东西需要改写.

注意p==st后,我们已经枚举完所有对踵点对了,此时可以直接跳出循环.

不跳的话stk[p]这个没有被赋值的点会被访问.....


这个模板没有特判一些奇妙的细节......也没有在意精度......特别注意.....


=w=







0 0
原创粉丝点击