点积与叉积

/*            点积和叉积
1、点积
   设点坐标A(x1,y1),B(x2,y2),C(x3,y3),D(x4,y4);
   向量AB=(x2-x1,y2-y1)=(xAB,yAB),|AB|=sqrt(xAB^2+yAB^2);
   向量CD=(x4-x3,y4-y3)=(xCD,yCD),|CD|=sqrt(xCD^2+yCD^2);
   向量AB与向量CD的点积为:AB●CD=xAB*xCD+yAB*yCD;
   AB●CD=|AB|]CD|cos(a):AB●CD=0 => AB与CD垂直
                         AB●CD<0 => AB与CD间夹角a成钝角
                         AB●CD>0 => AB与CD间夹角a成锐角
   点积可以计算向量的夹角和物理上的功W=|F||S|cos(a)=F●S;
2、叉积
   向量P1与向量P2的叉积:
     P1^P2=|x1   y1|=x1*y1-x2*y2=-P2^P1;
           |x2   y2|
   若向量P1在向量P2的顺时针方向,则叉积P1^P2>0;
   若向量P1在向量P2的逆时针方向,则叉积P1^P2<0;
   若向量P1与向量P2共线,则叉积P1^P2=0;
   设向量P1'=P1-P0,P2'=P2-P0,其中
   P1'=(x1',y1')=(x1-x0,y1-y0);
   P2'=(x2',y2')=(x2-x0,y2-y0);
   p1'^p2'=(x1-x0)(y2-y0)-(x2-x0)(y1-y0)
   如果叉积p1'^p2'为正,则相对于P0,P2的极角大于P1的极角;
   如果叉积p1'^p2'为负,则相对于P0,P2的极角小于P1的极角;
   如果叉积p1'^p2'为零,则相对于P0,P2的极角相等P1的极角(也就是P0P1和P0P2共线);
   叉积除了计算几何向量的方向关系、还计算以向量为相邻的边的平行四边形面积外,一棵用来计算多边形的面积。
   在力学中,可以计算力矩|M|=|r||F|sin(b)=F^r
*/



/*UVA 2290 poj 1106
   题意:给你半圆可以覆盖的最多点数
   设发射台为p0,由于发射台p0为轴心,可向任何方向旋转,因此任何点与p0间的直线
都可以作为半圆的下边界线。若p0pi所在的直线为半圆的下边界线,则位于半圆区
域的点pj必须同时满足下述两个条件:
   1、pj在 p0pj 为下界线的半圆一侧,即 p0pi p0pj>=0;
   2、pj与p0的距离不大于半径,即|p0pj|<=r;
   依次以i为基点,利用叉积统计位于p0pi逆时针方向且长度与p0的距离不大于发射半径
r点数Si;
   显然,半圆可以覆盖的最多点数s=max{Si}。0<i<=n;
*/
#include<iostream>
#include<cmath>
#include<cstring>
#include<algorithm>
using namespace std;
const double epsi=1e-10;//epsi=0.0000000001
//const double pi=acos(-1);
const int MAXN=50005;
struct Point
{
	double x,y;
	Point(double _x=0,double _y=0):x(_x),y(_y){}
	Point operator -(const Point &op2) const{
		return Point(x-op2.x,y-op2.y);
	}
	double operator^(const Point &op2) const{
		return x*op2.y-y*op2.x;
	}

};
inline int sign(const double &x)
{
	if(x>epsi) return 1;
	if(x<-epsi) return -1;
	return 0;
}
inline double sqr(const double &x)//计算x^2
{
	return x*x;
}
inline double mul(const Point &p0,const Point &p1,const Point &p2)//叉积
{
	return (p1-p0)^(p2-p0);
}
inline double dis2(const Point &p0,const Point &p1)
{
	return sqr(p0.x-p1.x)+sqr(p0.y-p1.y);//计算|p0p1|*|p0p1|
}
inline double dis(const Point &p0,const Point &p1)//计算|p0p1|
{
	return sqrt(dis2(p0,p1));
}
int n;
Point p[MAXN],cp;
double r;
int main()
{
	while(scanf("%lf%lf%lf",&cp.x,&cp.y,&r)&&r>=0)
	{
		scanf("%d",&n);
		int ans=0;
		int i;
		for(i=0;i<n;i++)
		{
			scanf("%lf%lf",&p[i].x,&p[i].y);
		}
		for(i=0;i<n;i++)
		{
			int tmp=0;
			for(int j=0;j<n;j++)
			{
				if(sign(dis(p[j],cp)-r)!=1)
				{
					if(sign(mul(cp,p[i],p[j]))!=-1) tmp++;
				}
			}
			ans=tmp>ans?tmp:ans;
		}
		printf("%d\n",ans);
	}
	return 0;
}




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

u014068781

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值