[地圖開發][算法及數據結構]四叉樹原理

參考:http://blog.csdn.net/zhouxuguang236/article/details/12312099

原博客地址還有c++源碼。。。

四叉樹索引的基本思想是將地理空間遞歸劃分為不同層次的樹結構。它將已知范圍的空間等分成四個相等的子空間,如此遞歸下去,直至樹的層次達到一定深度或者滿足某種要求后停止分割。四叉樹的結構比較簡單,并且當空間數據對象分布比較均勻時,具有比較高的空間數據插入和查詢效率,因此四叉樹是GIS中常用的空間索引之一。常規四叉樹的結構如圖所示,地理空間對象都存儲在葉子節點上,中間節點以及根節點不存儲地理空間對象。

?

?

四叉樹示意圖

?

四叉樹對于區域查詢,效率比較高。但如果空間對象分布不均勻,隨著地理空間對象的不斷插入,四叉樹的層次會不斷地加深,將形成一棵嚴重不平衡的四叉樹,那么每次查詢的深度將大大的增多,從而導致查詢效率的急劇下降。

?

本節將介紹一種改進的四叉樹索引結構。四叉樹結構是自頂向下逐步劃分的一種樹狀的層次結構。傳統的四叉樹索引存在著以下幾個缺點:

(1)空間實體只能存儲在葉子節點中,中間節點以及根節點不能存儲空間實體信息,隨著空間對象的不斷插入,最終會導致四叉樹樹的層次比較深,在進行空間數據窗口查詢的時候效率會比較低下。

(2)同一個地理實體在四叉樹的分裂過程中極有可能存儲在多個節點中,這樣就導致了索引存儲空間的浪費。

(3)由于地理空間對象可能分布不均衡,這樣會導致常規四叉樹生成一棵極為不平衡的樹,這樣也會造成樹結構的不平衡以及存儲空間的浪費。

相應的改進方法,將地理實體信息存儲在完全包含它的最小矩形節點中,不存儲在它的父節點中,每個地理實體只在樹中存儲一次,避免存儲空間的浪費。首先生成滿四叉樹,避免在地理實體插入時需要重新分配內存,加快插入的速度,最后將空的節點所占內存空間釋放掉。改進后的四叉樹結構如下圖所示。四叉樹的深度一般取經驗值4-7之間為最佳。

?

圖改進的四叉樹結構

?

為了維護空間索引與對存儲在文件或數據庫中的空間數據的一致性,作者設計了如下的數據結構支持四叉樹的操作。

(1)四分區域標識

分別定義了一個平面區域的四個子區域索引號,右上為第一象限0,左上為第二象限1,左下為第三象限2,右下為第四象限3。

typedef enum

{

??????UR = 0,// UR第一象限

??????UL = 1,?// UL為第二象限

??????LL = 2,?// LL為第三象限

??????LR = 3??// LR為第四象限

}QuadrantEnum;

(2)空間對象數據結構

空間對象數據結構是對地理空間對象的近似,在空間索引中,相當一部分都是采用MBR作為近似。

/*空間對象MBR信息*/

typedef struct SHPMBRInfo

{

??????int nID;???????//空間對象ID號

??????MapRect Box;????//空間對象MBR范圍坐標

}SHPMBRInfo;

nID是空間對象的標識號,Box是空間對象的最小外包矩形(MBR)。

(3)四叉樹節點數據結構

四叉樹節點是四叉樹結構的主要組成部分,主要用于存儲空間對象的標識號和MBR,也是四叉樹算法操作的主要部分。

/*四叉樹節點類型結構*/

typedef struct QuadNode

{

??????MapRect????????????Box;???????????????????//節點所代表的矩形區域

??????int????????????????nShpCount;????????//節點所包含的所有空間對象個數

??????SHPMBRInfo* pShapeObj;??????????//空間對象指針數組

??????int?????????nChildCount;????????????//子節點個數

??????QuadNode?*children[4];?????????????//指向節點的四個孩子

}QuadNode;

Box是代表四叉樹對應區域的最小外包矩形,上一層的節點的最小外包矩形包含下一層最小外包矩形區域;nShpCount代表本節點包含的空間對象的個數;pShapeObj代表指向空間對象存儲地址的首地址,同一個節點的空間對象在內存中連續存儲;nChildCount代表節點擁有的子節點的數目;children是指向孩子節點指針的數組。

?

?參考:http://blog.csdn.net/zhouxuguang236/article/details/12312099

四叉樹原理

四叉樹是種很直接的空間索引技術。在四叉樹中,每個節點表示覆蓋了部分進行索引的空間的邊界框,根節點覆蓋了整個區域。每個節點要么是葉節點,有包含一個或多個索引點的列表,沒有孩子。要么是內部節點,有四個孩子,每個孩子對應將區域沿兩根軸對半分得到的四個象限中的一個,四叉樹也因此得名。

圖1??? 展示四叉樹是怎樣劃分索引區域的 來源:維基百科

將數據插入四叉樹很簡單:從根節點開始,判斷你的數據點屬于哪個象限。遞歸到相應的節點,重復步驟,直到到達葉節點,然后將該點加入節點的索引點列表中。如果列表中的元素個數超出了預設的最大數目,則將節點分裂,將其中的索引點移動到相應的子節點中去。

圖2??? 四叉樹的內部結構

查詢四叉樹時從根節點開始,檢查每個子節點看是否與查詢的區域相交。如果是,則遞歸進入該子節點。當到達葉節點時,檢查點列表中的每一個項看是否與查詢區域相交,如果是則返回此項。

注意四叉樹是非常規則的,事實上它是一種字典樹,因為樹節點的值不依賴于插入的數據。因此我們可以用直接的方式給節點編號:用二進制給每個象限編號(左上是00,右上是10等等?譯者注:第一個比特位為0表示在左半平面,為1在右半平面。第二個比特位為0表示在上半平面,為1在下半平面),任一節點的編號是由從根開始,它的各祖先的象限號碼串接而成的。在這個編號系統中,圖2中右下角節點的編號是1101。

如果我們定義了樹的最大深度,不需通過樹就可以計算數據點所在節點的編號:只要把節點的坐標標準化到適當的整數區間中(比如32位整數),然后把轉化后x, y坐標的比特位交錯組合。每對比特指定了假想的四叉樹中的一個象限。

?

?

如何在iOS地圖上高效的顯示大量數據

參考:http://blog.163.com/l1_jun/blog/static/143863882013111651737708/

轉載于:https://www.cnblogs.com/lyggqm/p/5230733.html

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/373581.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/373581.shtml
英文地址,請注明出處:http://en.pswp.cn/news/373581.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

mongoDB中的數據類型

Date mongo shell中提供各式各樣的返回日期類型的方法,例如字符串類型或者Date對象類型: Date()返回當前的日期字符串;new Date()返回使用ISODate()包裝的Date對象類型;ISODate()返回使用ISODate()包裝的Date對象類型;…

C++ namespace

是否應該使用using(using namespace std) 注:我將namespace翻譯成姓或士族。選擇某個namespace中的變量、函數、組合類型,就像是在介紹某個人 姓 namespace, 名 variable。 參考: 1、Why is “using namespace std” considered bad practice…

按鍵 粘貼上一個命令_合并單元格、選擇性粘貼的快捷鍵都是啥?今天一次告訴你……...

經常有人在群里問,合并單元格的快捷鍵是什么?選擇性粘貼數值的快捷鍵是什么?今天就來聊聊快捷鍵的一些冷門知識……Alt鍵的作用快捷鍵其實就是一些組合鍵,主要用到Ctrl、shift、Alt這三個鍵其中之一或者是幾個,再加上其…

Spring MVC和JQuery用于Ajax表單驗證

在本教程中,我們將看到如何使用Ajax和Spring MVC和JQuery在服務器端驗證表單。 Spring MVC為通過注釋驅動的配置采用Ajax提供了非常方便的過程。 我們將使用此注釋驅動的配置以JSON數據的形式發送Ajax響應。 響應將包含表單驗證的狀態,并且表單數據中存在…

myeclipse10.7破解成功 但 無法打war包 提示:securecrt alert:integrity ch

myeclipse10.7破解成功 但 無法打war包 提示:securecrt alert:integritycheck error找了好久才找到解決辦法http://download.csdn.net/detail/yi303526230/6889101#comment本次對于myeclipse10破解后,導出war包時報“SECURITY ALERT: INTEGERITY CHECK E…

Mongodb的update操作

在前面的文章“mongodb 查詢的語法”里,我介紹了Mongodb的常用查詢語法,Mongodb的update操作也有點復雜,我結合自己的使用經驗,在這里介紹一下,給用mongodb的朋友看看,也方便以后自己用到的時候查閱&#x…

封裝方法

<?php class DBDA {public $host"localhost";public $uid"root";public $pwd"123";public $dbname"mydb";/***給一個sql語句&#xff0c;返回執行的結果*param string $sql 用戶指定的sql語句*param int $type 用戶給的語句類型&a…

AFNetwork 作用和使用方法具體解釋

轉自&#xff1a;http://www.maxiaoguo.com/clothes/269.html AFNetworking是一個輕量級的iOS網絡通信類庫。它建立在NSURLConnection和NSOperation等類庫的基礎上&#xff0c;讓非常多網絡通信功能的實現變得十分簡單。它支持HTTP請求和基于REST的網絡服務&#xff08;包含GET…

在MongoDB中存儲分層數據

繼續使用MongoDB進行 NoSQL之旅&#xff0c;我想觸摸一個經常出現的特定用例&#xff1a;存儲分層文檔關系。 MongoDB是很棒的文檔數據存儲&#xff0c;但是如果文檔具有父子關系怎么辦&#xff1f; 我們可以有效地存儲和查詢此類文檔層次結構嗎&#xff1f; 答案是肯定的&…

圖的深度遍歷

圖的深度遍歷 Time Limit: 1000MS Memory Limit: 65536KBSubmit StatisticProblem Description 請定一個無向圖&#xff0c;頂點編號從0到n-1&#xff0c;用深度優先搜索(DFS)&#xff0c;遍歷并輸出。遍歷時&#xff0c;先遍歷節點編號小的。Input 輸入第一行為整數n&#xff…

Linux學習筆記——gzip命令

這個 gzip 程序被用來壓縮一個或多個文件。當執行 gzip 命令時&#xff0c;則原始文件的壓縮版會替代原始文件。 相對應的 gunzip 程序被用來把壓縮文件復原為沒有被壓縮的版本。gzip 選項&#xff1a;選項 說明-c把輸出寫入到標準輸出&#xff0c;并且保留原始文件。也有可能用…

java集合類——Stack類

查看java的API文檔&#xff0c;Stack繼承Vector類。 棧的特點是后進先出。 API中Stack自身的方法不多&#xff0c;基本跟棧的特點有關。 Java代碼 import java.util.Stack; public class StackTest { public static void main(String[] args) { Stack&l…

免裝版_無縫貼圖制作軟件 PixPlant2中文免裝版

點擊上方藍字關注我們如您喜歡我們的公眾號&#xff0c;不妨推薦給身邊的朋友資源介紹&#xff1a;資源來源于網絡&#xff0c;很多時候我們從網上找的貼圖并不是無縫的&#xff0c;而且一般都沒有高光/法線貼圖這些&#xff0c;在材質的模擬上就要差了很多&#xff0c;在這里小…

網頁特效:用CSS3制作3D圖片立方體旋轉特效

<!DOCTYPE html> <html> <head> <meta charset"utf-8" /> <title>CSS3制作3D圖片立方體旋轉特效 - 站長素材</title><style type"text/css">html{background:linear-gradient(#ff0 0%,#F00 80%);height: 100%; …

Java中使用Map and Fold進行功能性編程

在函數式編程中&#xff0c;Map和Fold是兩個非常有用的運算符&#xff0c;它們屬于每種函數式語言。 如果Map和Fold運算符是如此強大且必不可少&#xff0c;那么您如何解釋說即使Java編程語言缺少這兩個運算符&#xff0c;我們也可以使用Java來完成工作&#xff1f; 事實是&…

Linux 文件壓縮解壓縮

文章來自&#xff1a;http://www.xuexiyuan.cn/article/detail/53.html *.tar格式 解包1&#xff1a;$ tar -xvf FileName.tar解包2&#xff1a;$ tar -xvf FileName.tar -C DirName# tar解壓縮到指定目錄打包&#xff1a;$ tar -cvf FileName.tar DirName# tar是打包&#x…

Mysql 分頁語句Limit用法

Mysql 分頁語句Limit用法 1、Mysql的limit用法 在我們使用查詢語句的時候&#xff0c;經常要返回前幾條或者中間某幾行數據&#xff0c;這個時候怎么辦呢&#xff1f;不用擔心&#xff0c;mysql已經為我們提供了這樣一個功能。 Sql代碼 SELECT * FROM table LIMIT [offset,] r…

sqlmap指定cookie_利用SQLMap進行cookie注入

SQLMap被稱為注入神器&#xff0c;N多大神都使用SQLmap來進行注入測試&#xff0c;我等小菜當然也會用來裝一下A*C&#xff0c;用了N久SQLMAP了&#xff0c;但是極少用 到cookie注入&#xff0c;一遇到cookie注入就去使用注入中轉工具&#xff0c;比較麻煩。剛好今天群里的USB問…

c語言else匹配問題

1 #include <stdio.h>2 #include <stdlib.h>3 4 //實現 依次輸入三個遞增的數 然后正確輸出5 6 //為什么得不到我們想要的結果呢 這就是else匹配的問題 當然了 在編譯器里面他會自動給你匹配7 //但是如果沒有了編譯器 筆試的時候呢。。。。8 //原因為&#xff1a;e…

Java:偽造工廠的閉包以創建域對象

最近&#xff0c;我們想要創建一個域對象&#xff0c;該對象需要具有外部依賴關系才能進行計算&#xff0c;并且希望能夠在測試中解決該依賴關系。 最初&#xff0c;我們只是在領域類中新建依賴項&#xff0c;但這使得無法在測試中控制其值。 同樣&#xff0c;我們似乎不應該將…