最近需要使用R樹做一下空間索引,在GeoSpark中使用了JTS庫中實現的STR樹,一開始以為是R-tree的一個變種,細看發現只是R樹的構建(packing)方式之一。
STR是Sort-Tile-Recursive的縮寫,是一種R-tree的packing算法。具體的介紹可以看作者的論文 https://www.cs.odu.edu/%7Emln/ltrs-pdfs/icase-1997-14.pdf ,CSDN上有個主要內容的翻譯 https://blog.csdn.net/qq_41775852/article/details/105405918。
R樹常見構建過程
通常R樹是針對動態有增刪的數據,因此構建過程可以將所有的數據逐個插入到R樹中。這種情況可能會存在一些缺點:
- (a) high load time
- (b) sub-optimal spac eutilization
- (c) poor R-tree structure requiring the retrieval of anunduly large number of nodes in order to satisfy a query.
因此,常用packing的方式自底向上的構建R樹,主要流程如下:
- 假設一共有r個矩形需要被索引,每個葉子結點中存儲的矩形數量為n。首先將所有的矩形分成r/n(此處取上界)個組;(分組方式通過下面的packing算法)
- 將各個分組寫入硬盤的pages,並計算每個分組內所有矩形的MBR以及分組對應的page-id;
- 對分組的MBR遞歸的執行上面的步驟,直到根節點。
在第1步中,將需要被索引的矩形分成r/n個組,論文中介紹了常見的Nearest-X(NX)、HilbertSort(HS)以及論文提出的Sort-Tile-Recursive(STR)。
STR算法
STR的算法本身並不復雜,以2維空間為例。對矩形的分組只考慮每個矩形的中心點,STR的基本思想是將所有的矩形以“tile”的方式分配到r/n(取上界)個分組中,此處的tile和網格類似。
首先,對矩形按x坐標排序,然后划分成 $\sqrt{r/n}$ 個slice。然后對slice內的矩形按y坐標排序,進一步划分成 $\sqrt{r/n}$ 份。
對於更高維的空間,可以按這種方式接着划分。
總結
這個算法就是這樣做一個簡單的划分,正如論文的標題 《STR: A Simple and Efficient Algorithm for R-Tree Packing》,有種方法對於一篇論文來講太簡單了的感覺。文章內還做了些對比實驗,表明針對不同的空間數據分布情況最好選擇對應合適的方法,STR的packing算法並不是適合所有的場景。
簡單點來看,也就是將空間中的矩形划分到了一個x、y方向相等的網格的分組中,當數據為長寬差距較大的矩形范圍分布時,做一個xy方向的分組數量相同應該不是最好的方案。