题意

一个k维空间,给出n个点的坐标,给出t个询问,每个询问给出一个点的坐标和一个m。对于每个询问找出跟这个点最接近的m个点

分析

kd树的模板题。

 #include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
#include <queue> using namespace std;
typedef long long LL;
const int maxn=;
const int K=;
int num,nownum,m;
LL ans;
struct kdNode{
LL x[K];
int div;
bool lef;
}Ans[];
struct Node{
kdNode a;
LL dis;
bool operator <(const Node &a)const{
return dis<a.dis;
}
Node(){}
Node(kdNode &tmp,LL d){
a=tmp;
dis=d;
}
};
int cmpNo;
bool cmp(kdNode a,kdNode b){
return a.x[cmpNo]<b.x[cmpNo];
}
inline LL max(LL a,LL b){//why?
return a>b?a:b;
}
kdNode p[maxn],q;
LL dis(kdNode a,kdNode b,int k){
LL res=;
for(int i=;i<k;i++){
res+=(a.x[i]-b.x[i])*(a.x[i]-b.x[i]);
}
return res;
}
priority_queue<Node>qq;
void buildKD(int l,int r,kdNode* p,int d,int k){
if(l>r)return ;
int m=(l+r)/;
cmpNo=d;
nth_element(p+l,p+m,p+r+,cmp);
p[m].div=d;
if(l==r){
p[m].lef=;
return ;
}
buildKD(l,m-,p,(d+)%k,k);
buildKD(m+,r,p,(d+)%k,k);
}
void findkd(int l,int r,kdNode& tar,kdNode* p,int k){
if(l>r)return;
int m=(l+r)/;
LL d=dis(p[m],tar,k);
if(p[m].lef){
if(nownum<num){
nownum++;
ans=max(ans,d);
qq.push(Node(p[m],d));
}
else if(ans>d){
qq.pop();
qq.push(Node(p[m],d));
ans=qq.top().dis;
}
return;
}
LL t=tar.x[p[m].div]-p[m].x[p[m].div];
if(t>){
findkd(m+,r,tar,p,k);
if(nownum<num){
qq.push(Node(p[m],d));
nownum++;
ans=qq.top().dis;
findkd(l,m-,tar,p,k);
}else{
if(ans>d){
qq.pop();
qq.push(Node(p[m],d));
ans=qq.top().dis;
}
if(ans>t*t)
findkd(l,m-,tar,p,k);
}
}else{
findkd(l,m-,tar,p,k);
if(nownum<num){
qq.push(Node(p[m],d));
nownum++;
ans=qq.top().dis;
findkd(m+,r,tar,p,k);
}else{
if(ans>d){
qq.pop();
qq.push(Node(p[m],d));
ans=qq.top().dis;
}
if(ans>t*t){
findkd(m+,r,tar,p,k);
}
}
}
} int n,k;
int main(){
while(scanf("%d%d",&n,&k)==){
for(int i=;i<n;i++){
for(int j=;j<k;j++){
scanf("%lld",&p[i].x[j]);
}
p[i].lef=;
}
buildKD(,n-,p,k-,k);
int t;
scanf("%d",&t);
for(int i=;i<=t;i++){
ans=-;
nownum=;
for(int j=;j<k;j++){
scanf("%lld",&q.x[j]);
}
while(!qq.empty())qq.pop();
scanf("%d",&num);
findkd(,n-,q,p,k);
for(int j=;j<=num;j++){
Ans[j]=qq.top().a;
qq.pop();
}
printf("the closest %d points are:\n",num);
for(int j=num;j>=;j--){
for(int kk=;kk<k;kk++){
if(kk==)
printf("%lld",Ans[j].x[kk]);
else
printf(" %lld",Ans[j].x[kk]);
}
printf("\n");
}
}
}
return ;
}

【hdu4347】The Closest M Points 【KD树模板】的更多相关文章

  1. bzoj 3053 HDU 4347 : The Closest M Points kd树

    bzoj 3053 HDU 4347 : The Closest M Points  kd树 题目大意:求k维空间内某点的前k近的点. 就是一般的kd树,根据实测发现,kd树的两种建树方式,即按照方差 ...

  2. hdu 4347 The Closest M Points (kd树)

    版权声明:本文为博主原创文章,未经博主允许不得转载. hdu 4347 题意: 求k维空间中离所给点最近的m个点,并按顺序输出  . 解法: kd树模板题 . 不懂kd树的可以先看看这个 . 不多说, ...

  3. [hdu4347]The Closest M Points(线段树形式kd-tree)

    解题关键:kdtree模板题,距离某点最近的m个点. #include<cstdio> #include<cstring> #include<algorithm> ...

  4. [hdu4347]The Closest M Points(平衡树式kdtree)

    解题关键:模板题(结合起来了) #include<iostream> #include<cstdio> #include<cstring> #include< ...

  5. BZOJ3053:The Closest M Points(K-D Teee)

    Description The course of Software Design and Development Practice is objectionable. ZLC is facing a ...

  6. BZOJ 3053: The Closest M Points(K-D Tree)

    Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 1235  Solved: 418[Submit][Status][Discuss] Descripti ...

  7. k-d树模板(BZOJ2648)

    实现了插入一个点,查询距某个位置的最近点. #include <cstdio> #include <algorithm> using namespace std; , inf ...

  8. tju_4147 kd树+最小生成树

    kd树模板+全图最小生成树 标签(空格分隔): kd树+最小生成树 题目链接 题意: k维太空中有n个点,每个点可以与距离它m近的点连边,现在给你一堆点,并给出坐标,现在要建立通信网络,一些可以互相到 ...

  9. HDU 5992 Finding Hotels(KD树)题解

    题意:n家旅店,每个旅店都有坐标x,y,每晚价钱z,m个客人,坐标x,y,钱c,问你每个客人最近且能住进去(非花最少钱)的旅店,一样近的选排名靠前的. 思路:KD树模板题 代码: #include&l ...

随机推荐

  1. gson-2.2.api简单

    使用gson的tojson和fromjson实现对象和json的转换 Gson gson = new Gson(); // Or use new GsonBuilder().create();     ...

  2. Beta阶段第1周/共2周 Scrum立会报告+燃尽图 06

    作业要求与 [https://edu.cnblogs.com/campus/nenu/2018fall/homework/2284] 相同 版本控制:https://git.coding.net/li ...

  3. Git 将代码恢复到一个历史的版本

    Git 将代码恢复到一个历史的版本 要把代码回到某个历史版本 比如 test有两种方法 暴力的方式 如果你的仓库是自己在用(不影响别人),那么你可以使用 git reset --hard <ta ...

  4. 如何检测MySQL中建立的索引是否生效

    使用方法,在select语句前加上explain就可以了: EXPLAIN SELECT surname,first_name form a,b WHERE a.id=b.id EXPLAIN列的解释 ...

  5. Linux内核调试

    1.控制台优先级配置cat /proc/sys/kernel/printk6 4 1 76是控制台的优先级,打印信息的优先级要比它高才能打印出.4是默认的优先级cat /var/log/message ...

  6. C编译相关

    1,#error在编译期进行警告判断 eg: #if USB_MAXCHILDREN > 31 /* 8*sizeof(unsigned long) - 1 和条件编译宏一起使用,在编译时就可以 ...

  7. 转 HTTP.SYS 详解

    http.sys 是一个位于Win2003和WinXP SP2中的操作系统核心组件, 能够让任何应用程序通过它提供的接口,以http协议进行信息通讯. 温馨提示:如果用户不慎删除了该驱动文件,不用担心 ...

  8. php in_array的坑

    今天做一个根据用户充值领礼包码的活动,遇到一个问题部分用户领礼包时会一直提示“系统错误,请稍后再试”,这是什么情况,一开始以为接口出错了,一番排查后发现了问题所在,是in_array坑了~~~ 情况大 ...

  9. 列名 'Discriminator' 无效 解决方案

     {"列名 'Discriminator' 无效.\r\n列名 'Discriminator' 无效.\r\n列名 'Discriminator' 无效.\r\n列名 'FileUrl' 无 ...

  10. eclipse调试时增加jvm参数

    下面的程中我们限制Java 堆的大小为20MB,不可扩展(将堆的最小值-Xms 参数与最大值-Xmx 参数设置为一样即可避免堆自动扩展),通过参数-XX:+HeapDumpOnOutOfMemoryE ...