题目大意:给你一个矩形的左上角和右下角的坐标,然后这个矩形有 N 个隔板分割成 N+1 个区域,下面有 M 组坐标,求出来每个区域包含的坐标数。

 
分析:做的第一道计算几何题目....使用叉积判断方向,然后使用二分查询找到点所在的区域。
 
代码如下:
============================================================================================================================
#include<stdio.h>
#include<math.h>
using namespace std; const int MAXN = 5e3+;
const double PI = acos(-1.0); struct point
{
double x, y; point(int x=, int y=):x(x), y(y){}
};
struct Vector
{
point a, b; void InIt(point t1, point t2){a=t1, b=t2;}
double operator * (const point &p) const
{
return (p.x-b.x)*(a.y-b.y) - (p.y-b.y)*(a.x-b.x);
}
}; Vector line[MAXN]; int Find(int N, point a)
{
int L=, R=N; while(L <= R)
{
int Mid = (L+R) >> ; if(line[Mid] * a < )
R = Mid - ;
else
L = Mid + ;
} return R;
} int main()
{
int M, N;
double x1, x2, y1, y2, ui, li; while(scanf("%d", &N) != EOF && N)
{
scanf("%d%lf%lf%lf%lf", &M, &x1, &y1, &x2, &y2); int ans[MAXN]={}; line[].InIt(point(x1, y1), point(x1, y2));
for(int i=; i<=N; i++)
{
scanf("%lf%lf", &ui, &li);
line[i].InIt(point(ui, y1), point(li, y2));
}
while(M--)
{
scanf("%lf%lf", &ui, &li);
int i = Find(N, point(ui, li)); ans[i] += ;
} for(int i=; i<=N; i++)
printf("%d: %d\n", i, ans[i]);
printf("\n");
} return ;
}

重写...

#include<math.h>
#include<stdio.h>
#include<vector>
#include<iostream>
#include<algorithm>
using namespace std; const double EPS = 1e-;
const int maxn = ; int SIGN(const double &val)
{///整数返回1,负数返回-1, 0返回0
if(val > EPS)return ;
if(fabs(val) < EPS)return ;
return -;
} class Point
{
public:
Point(double x, double y): x(x), y(y){}
Point operator- (const Point& other)const
{///重载减号
return Point((x-other.x), (y - other.y));
}
double operator^(const Point& other)const
{///重载异或,定义叉积的运算
return (x*other.y) - (y*other.x);
}
public:
double x, y;
}; class Segment
{
public:
Segment(Point S, Point E) : S(S), E(E){}
int Mul(Point& other) const
{///用差乘判断点在线段的方向
return SIGN( (E-S)^(other-S) );
}
public:
Point S, E;
}; class SetSegment
{///定义一个线段的集合,有很多线段构成
public:
void Insert(const Segment& other)
{///插入一个线段
segs.push_back(other);
}
unsigned int Find(Point p)
{///查找点p靠近的最左边的线段的下标
unsigned int L=, R=segs.size()-, M; while(L <= R)
{
M = (L+R) / ;
Segment tmp = segs[M];
if(tmp.Mul(p) == -)
R = M-;
else
L = M+;
} return R;
}
public:
vector<Segment> segs;
};
int main()
{
int N, M;
double x1, x2, y1, y2, Ui, Li; while(scanf("%d", &N) != EOF && N)
{
scanf("%d%lf%lf%lf%lf", &M, &x1, &y1, &x2, &y2); SetSegment ss; ss.Insert(Segment(Point(x1, y1), Point(x1, y2)));
for(int i=; i<N; i++)
{
scanf("%lf%lf", &Ui, &Li);
ss.Insert(Segment(Point(Ui, y1), Point(Li, y2)));
} int ans[maxn] = {}; while(M--)
{
scanf("%lf%lf", &x1, &y1); int index = ss.Find(Point(x1, y1));
ans[index] += ;
} for(int i=; i<=N; i++)
printf("%d: %d\n", i, ans[i]);
printf("\n");
} return ;
}

TOYS - POJ 2318(计算几何,叉积判断)的更多相关文章

  1. TOYS POJ 2318 计算几何 叉乘的应用

    Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 15060   Accepted: 7270 Description Calc ...

  2. POJ 2318/2398 叉积性质

    2318 2398 题意:给出n条线将一块区域分成n+1块空间,再给出m个点,询问这些点在哪个空间里. 思路:由于只要求相对位置关系,而对具体位置不关心,那么易使用叉积性质得到相对位置关系(左侧/右侧 ...

  3. POJ 2398--Toy Storage(叉积判断,二分找点,点排序)

    Toy Storage Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 6534   Accepted: 3905 Descr ...

  4. POJ 2318 TOYS(叉积+二分)

    题目传送门:POJ 2318 TOYS Description Calculate the number of toys that land in each bin of a partitioned ...

  5. 向量的叉积 POJ 2318 TOYS & POJ 2398 Toy Storage

    POJ 2318: 题目大意:给定一个盒子的左上角和右下角坐标,然后给n条线,可以将盒子分成n+1个部分,再给m个点,问每个区域内有多少各点 这个题用到关键的一步就是向量的叉积,假设一个点m在 由ab ...

  6. POJ 2318 TOYS【叉积+二分】

    今天开始学习计算几何,百度了两篇文章,与君共勉! 计算几何入门题推荐 计算几何基础知识 题意:有一个盒子,被n块木板分成n+1个区域,每个木板从左到右出现,并且不交叉. 有m个玩具(可以看成点)放在这 ...

  7. POJ 2398 Toy Storage(计算几何,叉积判断点和线段的关系)

    Toy Storage Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 3146   Accepted: 1798 Descr ...

  8. POJ 2318 TOYS (叉积+二分)

    题目: Description Calculate the number of toys that land in each bin of a partitioned toy box. Mom and ...

  9. poj 2318(叉积判断点在线段的哪一侧)

    TOYS Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 13120   Accepted: 6334 Description ...

随机推荐

  1. JavaScript上下文和闭包

    "this" 上下文 上下文通常是取决于一个函数如何被调用.当函数作为对象的方法被调用时,this 被设置为调用方法的对象: var object = { foo: functio ...

  2. JS常用的7中跨域方式总结

    javascript跨域有两种情况:  1.基于同一父域的子域之间,如:a.c.com和b.c.com  2.基于不同的父域之间,如:www.a.com和www.b.com  3.端口的不同,如:ww ...

  3. AngularJS cookie的使用

    Javascript使用document.cookie接口来处理简单的文本cookie,但现在大多数现代浏览器都可以使用html5 API了(sessionstorage和localstorage), ...

  4. HDU 1429 胜利大逃亡(续)(DP + 状态压缩)

    胜利大逃亡(续) Problem Description Ignatius再次被魔王抓走了(搞不懂他咋这么讨魔王喜欢)…… 这次魔王汲取了上次的教训,把Ignatius关在一个n*m的地牢里,并在地牢 ...

  5. java.net.ServerSocket和java.net.Socket

    个人博客地址:http://www.cnblogs.com/wdfwolf3/ java.net.ServerSocket 1.构造函数 a.ServerSocket() 创建一个无连接的server ...

  6. Unity NGUI和UGUI与模型、特效的层级关系

    目录 1.介绍两大UI插件NGUI和UGUI 2.unity渲染顺序控制方式 3.NGUI的控制 4.UGUI的控制 5.模型深度的控制 6.粒子特效深度控制 7.NGUI与模型和粒子特效穿插层级管理 ...

  7. PHP实现中文字串截取无乱码的方法

    直接使用PHP函数substr截取中文字符可能会出现乱码,主要是substr可能硬生生的将一个中文字符“锯”成两半.解决办法: 1.使用mbstring扩展库的mb_substr截取就不会出现乱码了. ...

  8. 关于 Log4Net

    Log4Net是用来记录日志的,可以将程序运行过程中的信息输出到一些地方(文件.数据库.EventLog等),日志就是程序的黑匣子,可以通过日志查看系统的运行过程,从而发现系统的问题.日志的作用:将运 ...

  9. Codeforces Round #204 (Div. 2): A

    超级大水题: 只要用到一个小学用过的结论就可:能被9整除的数它的各位数相加能被9整除: 代码: #include<iostream> #define maxn 1005 using nam ...

  10. 试试Navicat和Axere RP Pro吧

    感觉在作头作起和沟通方面,这些东东真是提高不好效率呢~~~ 由于敏感,只作载图.