最近在弄GPS的东西,写了个GPS算法,模拟测试10万个数据源。之前详细了解过geohash,我在这算法的基础上优化了算法。
如下是我程序输出的:
初始化 100000 个GPS 共消耗 172 毫秒
100000个GPS 更新 10次共消耗 1031 毫秒
在 100000 个GPS中执行矩形区域查询 100000 次,共消耗 687 毫秒
查询结果如下:15
57664 48341 6169 35905 43516 27668 13827 62139
94970 82370 2894 42013 40754 63631 53433
具体的测试代码如下:
#define GPS_MAX 10*10000
#define UPDATE_COUNT 10
#define SEARCH_TIMES 10*10000
typedef struct GpsPos_tag
{
int val;
double lat;
double lng;
double vdirection;
double hdirection;
}GpsPos;
void TestSegmentationIndex()
{
SegmentationIndex index;
GpsPos *gps = new GpsPos[GPS_MAX];
double wlng = 115.00;
double elng = 120.00;
double slat = 34.0;
double nlat = 36.0;
double ilng = (elng - wlng)/100000;
double ilat = (nlat - slat)/100000;
double lat;
double lng;
DWORD st;
int results[100];
int count = 0;
srand(GetTickCount());
st = GetTickCount();
for (int i=0;i<GPS_MAX;i++)
{
gps[i].lat = slat + (nlat - slat)*rand()/RAND_MAX;
gps[i].lng = wlng + (elng - wlng)*rand()/RAND_MAX;
gps[i].val = i;
gps[i].hdirection = (rand()&1) ? -1.0 : 1.0;
gps[i].vdirection = (rand()&1) ? -1.0 : 1.0;
index.InsertItem(gps[i].lat,gps[i].lng,gps[i].val);
}
printf("初始化 %d 个GPS 共消耗 %d 毫秒\n\n",GPS_MAX,GetTickCount() - st);
st = GetTickCount();
for (int k=0;k<10;k++)
{
for (int i=0;i<GPS_MAX;i++)
{
index.RemoveIndex(gps[i].lat,gps[i].lng,gps[i].val);
lat = gps[i].lat + gps[i].vdirection * ilat;
if (lat < slat || lat > nlat)//调整方向
{
gps[i].vdirection = gps[i].vdirection * (-1.0);
}
lng = gps[i].lng + gps[i].hdirection * ilng;
if (lng < wlng || lng > elng)//调整方向
{
gps[i].hdirection = gps[i].hdirection * (-1.0);
}
gps[i].lng = lng;
gps[i].lat = lat;
index.InsertItem(gps[i].lat,gps[i].lng,gps[i].val);
}
}
printf("%d个GPS 更新 %d次共消耗 %d 毫秒\n\n",GPS_MAX,UPDATE_COUNT,GetTickCount() - st);
//计算查询时间
memset(results,0,sizeof(results));
st = GetTickCount();
wlng = 115.00 + 2.5;
elng = 120.00 - 2;
slat = 34.0 + 1.0;
nlat = 36.0 - 0.5;
for (int i=0;i<10*10000;i++)
{
count = index.Search(117.500,117.550,35.00,35.05,results,100);
}
printf("在 %d 个GPS中执行矩形区域查询 %d 次,共消耗 %d 毫秒\n\n",GPS_MAX,SEARCH_TIMES,GetTickCount() - st);
printf("查询结果如下:%d\n",count);
for (int i=0;i<count;i++)
{
printf("%d\t",results[i]);
if (((i+1)%8) == 0)
{
printf("\n");
}
}
}
int _tmain(int argc, _TCHAR* argv[])
{
TestSegmentationIndex();
getchar();
return 0;
}
网上有KD树等用于附近点查询的算法,现在还没看懂,正在研究中。如果对我这算法感兴趣,可以与我联系:wjh_2010@163.com
如下是我程序输出的:
初始化 100000 个GPS 共消耗 172 毫秒
100000个GPS 更新 10次共消耗 1031 毫秒
在 100000 个GPS中执行矩形区域查询 100000 次,共消耗 687 毫秒
查询结果如下:15
57664 48341 6169 35905 43516 27668 13827 62139
94970 82370 2894 42013 40754 63631 53433
具体的测试代码如下:
#define GPS_MAX 10*10000
#define UPDATE_COUNT 10
#define SEARCH_TIMES 10*10000
typedef struct GpsPos_tag
{
int val;
double lat;
double lng;
double vdirection;
double hdirection;
}GpsPos;
void TestSegmentationIndex()
{
SegmentationIndex index;
GpsPos *gps = new GpsPos[GPS_MAX];
double wlng = 115.00;
double elng = 120.00;
double slat = 34.0;
double nlat = 36.0;
double ilng = (elng - wlng)/100000;
double ilat = (nlat - slat)/100000;
double lat;
double lng;
DWORD st;
int results[100];
int count = 0;
srand(GetTickCount());
st = GetTickCount();
for (int i=0;i<GPS_MAX;i++)
{
gps[i].lat = slat + (nlat - slat)*rand()/RAND_MAX;
gps[i].lng = wlng + (elng - wlng)*rand()/RAND_MAX;
gps[i].val = i;
gps[i].hdirection = (rand()&1) ? -1.0 : 1.0;
gps[i].vdirection = (rand()&1) ? -1.0 : 1.0;
index.InsertItem(gps[i].lat,gps[i].lng,gps[i].val);
}
printf("初始化 %d 个GPS 共消耗 %d 毫秒\n\n",GPS_MAX,GetTickCount() - st);
st = GetTickCount();
for (int k=0;k<10;k++)
{
for (int i=0;i<GPS_MAX;i++)
{
index.RemoveIndex(gps[i].lat,gps[i].lng,gps[i].val);
lat = gps[i].lat + gps[i].vdirection * ilat;
if (lat < slat || lat > nlat)//调整方向
{
gps[i].vdirection = gps[i].vdirection * (-1.0);
}
lng = gps[i].lng + gps[i].hdirection * ilng;
if (lng < wlng || lng > elng)//调整方向
{
gps[i].hdirection = gps[i].hdirection * (-1.0);
}
gps[i].lng = lng;
gps[i].lat = lat;
index.InsertItem(gps[i].lat,gps[i].lng,gps[i].val);
}
}
printf("%d个GPS 更新 %d次共消耗 %d 毫秒\n\n",GPS_MAX,UPDATE_COUNT,GetTickCount() - st);
//计算查询时间
memset(results,0,sizeof(results));
st = GetTickCount();
wlng = 115.00 + 2.5;
elng = 120.00 - 2;
slat = 34.0 + 1.0;
nlat = 36.0 - 0.5;
for (int i=0;i<10*10000;i++)
{
count = index.Search(117.500,117.550,35.00,35.05,results,100);
}
printf("在 %d 个GPS中执行矩形区域查询 %d 次,共消耗 %d 毫秒\n\n",GPS_MAX,SEARCH_TIMES,GetTickCount() - st);
printf("查询结果如下:%d\n",count);
for (int i=0;i<count;i++)
{
printf("%d\t",results[i]);
if (((i+1)%8) == 0)
{
printf("\n");
}
}
}
int _tmain(int argc, _TCHAR* argv[])
{
TestSegmentationIndex();
getchar();
return 0;
}