<code> 二维空间下的最近点对查找

  1 // space_minum.cpp : Defines the entry point for the console application.
  2 //
  3 #include <iostream>
  4 #include <math.h>
  5  
  6 using namespace std;
  7  
  8 float minu=10000000;
  9 int fff,bbb;
 10  
 11 void Insertsort(float list[],float X[],int a,int b);
 12 void Insertsort(float list[],float X[],int a,int b){
 13     float next,tmp;//插入排序,对xy坐标组按照x坐标排序
 14     int j;
 15     if(a>b)return;
 16     for(int x=a;x<=b;x++){
 17     next=list[x];
 18     tmp=X[x];
 19     for(j=x-1;j>=a&&next<list[j];j--)
 20     {list[j+1]=list[j];
 21     X[j+1]=X[j];
 22     }
 23     list[j+1]=next;
 24     X[j+1]=tmp;
 25     }
 26  
 27 }
 28  
 29 float Dis(float x1,float y1,float x2,float y2){
 30 float ans=sqrt((x1-x2)*(x1-x2)+(y1-y2)*(y1-y2));
 31 return ans;
 32 }
 33  
 34 int find_tmp(int mid,int limit,float dis,char updown,float x[]){
 35     int i=mid;
 36 if(updown=='f'){//向前搜索
 37     for(i;i>=limit&&x[mid]-dis<x[i];i--);
 38 return i;
 39 }
 40 else if(updown=='b'){//向后搜索
 41     for(i;i<=limit&&x[mid]+dis>x[i];i++);
 42 return i;
 43 }
 44  
 45 }
 46  
 47  
 48  
 49  
 50 float seperate(float x[],float y[],int left,int right){
 51 int mid=(left+right)/2;
 52 float dis=minu;
 53  
 54 if(right-left==0)return dis;
 55 else if(right-left==1) {
 56     float t=Dis(x[right],y[right],x[left],y[left]);
 57         if(t<minu){minu=t;fff=right;bbb=left;}
 58     return t;
 59 }
 60 else {
 61     float ll=seperate(x,y,left,mid);
 62     float rr=seperate(x,y,mid,right);
 63     if(ll<rr)dis=ll;else dis=rr;
 64     if(minu<dis)dis=minu;//修改为在以计算过的点中最小值,而非该划分中的最小值,提高速度
 65      
 66     float t_mid=x[mid];//从划分元拓展dis单位
 67     int f,b;
 68     f=find_tmp(mid,left,dis,'f',x);//向前向后搜索查找范围内元素
 69     b=find_tmp(mid,right,dis,'b',x);
 70  
 71  
 72     //从mid-f个点依次选出点与b-mid个点计算最小值
 73 //注:已经按照x坐标进行排序,当x[b]-x[f]中点>=dis时,f++,b从mid重新开始
 74  
 75 float tmp=0;
 76 for(int i=f;i<mid;i++){
 77     for(int j=mid;j<=b;j++){//修改比较条件j<=b&&j-mid<=6,原因已在文档中说明
 78     if(x[j]-x[i]<dis)
 79         tmp =Dis(x[i],y[i],x[j],y[j]);
 80     else break;
 81     if(tmp!=0&&tmp<dis){dis=tmp;minu=tmp;
 82     //cout<<i<<' '<<fff<<' ';
 83     fff=i;bbb=j;
 84     }
 85     }
 86 }
 87  
 88 return dis;
 89  
 90  
 91 //  float t=0;for(int i=f;i<=mid;i++){for(int j=mid;j<=b;j++){
 92 //  t =Dis(x[i],y[i],x[j],y[j]);if(t!=0&&t<dis)dis=t;}}return dis;
 93  
 94 }
 95 }
 96  
 97  
 98  
 99  
100 const int   max=20;
101 int main(int argc, char* argv[])
102 {
103  
104 float x[max];
105 float y[max];
106 cout<<"输入点对数";
107 int n;
108 cin>>n;
109 cout<<"输入图中点坐标x,y"<<endl;
110 for(int i=0;i<n;i++)
111 cin>>x[i]>>y[i];
112 //for(i=0;i<n;i++)
113 //cout<<x[i]<<' '<<y[i];
114 //按照x坐标排序,用于划分
115 Insertsort(x,y,0,n-1);
116 //for(i=0;i<n;i++)
117 //cout<<x[i]<<' '<<y[i]<<'|';cout<<endl;
118  
119 cout<<seperate(x,y,0,n-1)<<endl;
120 cout<<'['<<x[fff]<<','<<y[fff]<<']'<<endl;
121 cout<<'['<<x[bbb]<<','<<y[bbb]<<']'<<endl;
122     return 0;
123 }

 

posted @ 2013-04-15 22:09  SONGHY  阅读(306)  评论(0编辑  收藏  举报