时间限制:5.0s   内存限制:256.0MB  
总提交次数:547  
AC次数:137   平均分:40.31
将本题分享到:
      
试题来源
  2012中国国家集训队命题答辩
问题描述
  平面上有n个点。现在有m次询问,每次给定一个点(px, py)和一个整数k,输出n个点中离(px, py)的距离第k大的点的标号。如果有两个(或多个)点距离(px, py)相同,那么认为标号较小的点距离较大。
输入格式
  第一行,一个整数n,表示点的个数。

  下面n行,每行两个整数x_i, y_i,表示n个点的坐标。点的标号按照输入顺序,分别为1..n。

  下面一行,一个整数m,表示询问个数。

  下面m行,每行三个整数px_i, py_i, k_i,表示一个询问。
输出格式
  m行,每行一个整数,表示相应的询问的答案。
样例输入
3

0 0

0 1

0 2

3

1 1 2

0 0 3

0 1 1
样例输出
3

1

1
数据规模和约定
  50%的数据中,n个点的坐标在某范围内随机分布。

  100%的数据中,n<=10^5, m<=10^4, 1<=k<=20,所有点(包括询问的点)的坐标满足绝对值<=10^9,n个点中任意两点坐标不同,m个询问的点的坐标在某范围内随机分布。

【题解】

kd-tree。

注意求的是第k“远"

在找到时候用一个队列维护当前找到的前k远的距离(因为k最大只有20,所以不用写恶心的二分检索了)。

即dl[1..k],其中dl[k]是第k远,dl[1]是最远的。

然后估价函数的判断变成

gujia[某个方向] >= dl[k]

满足则继续往那个方向找。

ma_x[2],mi_n[2]是某个子树的里面点的坐标最大可能形成的矩形的左上角和右上角坐标。

[0]是x,[1]是y;

【代码】

#include <cstdio>
#include <algorithm>
#include <cmath>
#include <cstring>
using namespace std;
const int MAXN = 150000;
const int MAXK = 30;
struct point
{
long long d[2], ma_x[2], mi_n[2];
int l, r, id;
};
struct ddl
{
long long dis;
int id;
};
int n, root, now, k;
point t[MAXN], p[MAXN], op;
long long x[MAXN], y[MAXN];
ddl dl[MAXK];
bool cmp(point a, point b)
{
if (a.d[now] < b.d[now])
return true;
return false;
}
void push_up(int rt)
{
int l = t[rt].l, r = t[rt].r;
for (int i = 0; i <= 1; i++)
{
if (l)
{
t[rt].ma_x[i] = max(t[rt].ma_x[i], t[l].ma_x[i]);
t[rt].mi_n[i] = min(t[rt].mi_n[i], t[l].mi_n[i]);
}
if (r)
{
t[rt].ma_x[i] = max(t[rt].ma_x[i], t[r].ma_x[i]);
t[rt].mi_n[i] = min(t[rt].mi_n[i], t[r].mi_n[i]);
}
}
}
int build(int begin, int end, int fx)
{
int m = (begin + end) >> 1;
now = fx;
nth_element(p + begin, p + m, p + end + 1, cmp);//左闭右开区间
t[m] = p[m];
for (int i = 0; i <= 1; i++)
t[m].ma_x[i] = t[m].mi_n[i] = p[m].d[i];
if (begin < m)
t[m].l = build(begin, m - 1, 1 - fx);
if (m < end)
t[m].r = build(m + 1, end, 1 - fx);
push_up(m);
return m;
}
void input_data()
{
scanf("%d", &n);
for (int i = 1; i <= n; i++)
{
scanf("%lld%lld", &x[i], &y[i]);
p[i].d[0] = x[i];
p[i].d[1] = y[i];
p[i].id = i;
}
root = build(1, n, 0);
}
long long get_dis(point a, point b)
{
return (a.d[0] - b.d[0])*(a.d[0] - b.d[0]) + (a.d[1] - b.d[1])*(a.d[1] - b.d[1]);
}
long long gujia_max(int rt)
{
long long temp = 0;
for (int i = 0; i <= 1; i++)
temp += max((t[rt].ma_x[i] - op.d[i])*(t[rt].ma_x[i] - op.d[i]), (t[rt].mi_n[i] - op.d[i])*(t[rt].mi_n[i] - op.d[i]));
return temp;
}
void query(int rt)
{
long long dis = get_dis(t[rt], op);
int tempk = k;
while (dl[tempk].dis < dis || (dl[tempk].dis == dis && t[rt].id < dl[tempk].id))
{
tempk--;
if (!tempk)
break;
}
if (tempk != k) //比第k远的大。就看看它是第几远。
{
for (int i = k; i >= tempk + 2; i--)
dl[i] = dl[i - 1];
dl[tempk + 1].dis = dis;
dl[tempk + 1].id = t[rt].id;
}
long long gl = -2, gr = -2;
int l = t[rt].l, r = t[rt].r;
if (l)
gl = gujia_max(l);
if (r)
gr = gujia_max(r);
if (gl < gr)
{
if (dl[k].dis <= gr) //注意估价函数的判断
query(r);
if (dl[k].dis <= gl)
query(l);
}
else
{
if (dl[k].dis <= gl)
query(l);
if (dl[k].dis <= gr)
query(r);
}
}
void output_ans()
{
int m;
scanf("%d", &m);
for (int i = 1; i <= m; i++)
{
memset(dl, 255, sizeof(dl));
scanf("%lld%lld%d", &op.d[0], &op.d[1], &k);
query(root);
printf("%d\n", dl[k].id);
}
}
int main()
{
//freopen("F:\\rush.txt", "r", stdin);
input_data();
output_ans();
return 0;
}

【24.91】【Tsinsen 1302】&【BZOJ 2626】JZPFAR的更多相关文章

  1. 【BZOJ 2749】 2749: [HAOI2012]外星人 (数论-线性筛?类积性函数)

    2749: [HAOI2012]外星人 Description Input Output 输出test行,每行一个整数,表示答案. Sample Input 1 2 2 2 3 1 Sample Ou ...

  2. 纳税服务系统【用户模块之使用POI导入excel、导出excel】

    前言 再次回到我们的用户模块上,我们发现还有两个功能没有完成: 对于将网页中的数据导入或导出到excel文件中,我们是完全没有学习过的.但是呢,在Java中操作excel是相对常用的,因此也有组件供我 ...

  3. C# 获取 mp3文件信息【包括:文件大小、歌曲长度、歌手、专辑】

    C# 获取 mp3文件信息[包括:文件大小.歌曲长度.歌手.专辑] 第一种方式:[代码已验证] // http://bbs.csdn.net/topics/390392612   string fil ...

  4. 【BZOJ 2194】2194: 快速傅立叶之二(FFT)

    2194: 快速傅立叶之二 Time Limit: 10 Sec  Memory Limit: 259 MBSubmit: 1273  Solved: 745 Description 请计算C[k]= ...

  5. 【BZOJ 4663】 (最小割)

    4663: Hack Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 69  Solved: 26 Description 由于 FZYZ 教学区禁止使 ...

  6. 【无私分享:从入门到精通ASP.NET MVC】从0开始,一起搭框架、做项目 目录索引

    索引 [无私分享:从入门到精通ASP.NET MVC]从0开始,一起搭框架.做项目(1)搭建MVC环境 注册区域 [无私分享:从入门到精通ASP.NET MVC]从0开始,一起搭框架.做项目(2)创建 ...

  7. 【如何快速的开发一个完整的iOS直播app】(原理篇)

    原文转自:袁峥Seemygo    感谢分享.自我学习 目录 [如何快速的开发一个完整的iOS直播app](原理篇) [如何快速的开发一个完整的iOS直播app](播放篇) [如何快速的开发一个完整的 ...

  8. 推荐一个算法编程学习中文社区-51NOD【算法分级,支持多语言,可在线编译】

    最近偶尔发现一个算法编程学习的论坛,刚开始有点好奇,也只是注册了一下.最近有时间好好研究了一下,的确非常赞,所以推荐给大家.功能和介绍看下面介绍吧.首页的标题很给劲,很纯粹的Coding社区....虽 ...

  9. 【MyEclipse 2015】 逆向破解实录系列【终】(纯研究)

    声明 My Eclipse 2015 程序版权为Genuitec, L.L.C所有. My Eclipse 2015 的注册码.激活码等授权为Genuitec, L.L.C及其付费用户所有. 本文只从 ...

随机推荐

  1. R 语言下常用第三方库的说明

    1. doBy 官方文档见 CRAN - Package doBy doBy 主要适用于以下操作: 1) Facilities for groupwise computations of summar ...

  2. Codefroces 784 愚人节题目(部分)

    A. Numbers Joke time limit per test 2 seconds memory limit per test 64 megabytes input standard inpu ...

  3. 读书笔记-Java设计模式

    本文来自http://blog.csdn.net/liuxian13183/ ,引用必须注明出处! Java的封装性很好,拿访问控制符来讲,没有权限的类或方法是不能访问的.如public,都可访问:p ...

  4. windows系统自带工具

    辅助功能向导:单击"開始→执行",在弹出的对话框中输入:accwiz 计算器:单击"開始→执行",在弹出的对话框中输入:calc 字符影射表:单击"開 ...

  5. js进阶 14-9 ajax事件有哪些

    js进阶 14-9 ajax事件有哪些 一.总结 一句话总结:ajax开始时事件.发送时事件,请求完成时事件,请求成功时事件,请求结束时事件,请求错误时事件事件. 1.ajax事件的监听对象是谁? 都 ...

  6. hbs模板(zmaze ui用的)

    hbs模板(zmaze ui用的) 一.总结 1.模板引擎:就是来生成界面的啊,只不过实现了view和数据分离以及一些其它的功能(预加载等). 2.Handlebars :但他是一个单纯的模板引擎,在 ...

  7. 105.UDP通信实现广播

    客户端 #include <stdio.h> #include <string.h> #include <winsock.h> #pragma comment(li ...

  8. Android Notification.setLatestEventInfo弃用和Notification.Builder用法

    今天在学习小米便签的源码的时候,至于源码的地址,http://m.blog.csdn.net/article/details?id=50544248 ,里面有好多github的开源项目,打开项目,报错 ...

  9. 使用ILMerge将所有引用的DLL和exe文件打成一个exe文件

    今天做了一个IM自动更新的软件,里面牵扯到了文件的解压和接口签名加密,使用了2个第三方的dll,想发布的时候才发现调用的类没几个,就像把它们都跟EXE文件打包在一起,以后复制去别的地方用也方便,于是上 ...

  10. windows CE项目开发

    软件列表 1.Windows mobile 设备中心 2.Microsoft visual Studio 2008 3.串口调试工具(sscom42.exe) 4.Wince 6.0模拟器 5.vir ...