Statistics
| Revision:

svn-gvsig-desktop / branches / v2_0_0_prep / libraries / libFMap_spatialindex / src / org / gvsig / fmap / data / index / spatial / spatialindex / RTreeSptLib.java @ 23803

History | View | Annotate | Download (6.6 KB)

1
package org.gvsig.fmap.data.index.spatial.spatialindex;
2

    
3
import java.io.File;
4
import java.io.FileNotFoundException;
5
import java.io.IOException;
6
import java.util.ArrayList;
7
import java.util.Iterator;
8
import java.util.List;
9

    
10
import org.gvsig.fmap.data.ReadException;
11
import org.gvsig.fmap.data.feature.Feature;
12
import org.gvsig.fmap.data.index.IndexException;
13
import org.gvsig.fmap.data.index.IndexParameters;
14
import org.gvsig.fmap.data.index.spatial.AbstractIntBasedSpatialIndex;
15
import org.gvsig.fmap.data.index.spatial.NearestNeighbourFinder;
16
import org.gvsig.fmap.data.index.spatial.PersistentSpatialIndex;
17
import org.gvsig.fmap.geom.Geometry;
18
import org.gvsig.fmap.geom.primitive.Envelope;
19
import org.gvsig.fmap.geom.primitive.Point2D;
20

    
21
import com.vividsolutions.jts.index.quadtree.Quadtree;
22

    
23
import spatialindex.rtree.RTree;
24
import spatialindex.spatialindex.IData;
25
import spatialindex.spatialindex.INode;
26
import spatialindex.spatialindex.IVisitor;
27
import spatialindex.spatialindex.Region;
28
import spatialindex.storagemanager.DiskStorageManager;
29
import spatialindex.storagemanager.IBuffer;
30
import spatialindex.storagemanager.IStorageManager;
31
import spatialindex.storagemanager.PropertySet;
32
import spatialindex.storagemanager.RandomEvictionsBuffer;
33

    
34
/**
35
 * <p>
36
 * RTree spatial index based in spatial index library: <br>
37
 * http://u-foria.org/marioh/spatialindex/index.html <br>
38
 * marioh@cs.ucr.edu
39
 * </p>
40
 * It has the problem that spatial index file creation is a bit slowly
41
 * (in comparation with other indexes).
42
 */
43
public class RTreeSptLib extends AbstractIntBasedSpatialIndex implements PersistentSpatialIndex,
44
                                                                        NearestNeighbourFinder{
45
        /**
46
         * Page size of associated file
47
         */
48
        private static final int defaultPageSize = 32 * 1024;
49
        private static final double defaultFillFactor = 0.85d;
50

    
51
        /**
52
         * Size of memory buffer of the index
53
         */
54
        private static final int BUFFER_SIZE = 25000;
55
        RTree rtree;
56
        //String rtreeFile;
57
        IStorageManager diskfile;
58
        /**
59
         * Constructor
60
         * @param overwriteFile tells if we must override existing files.
61
         * If we are goint to create a new spatial index (or if we want to overwrite
62
         * an existing one) we must to use always 'true'. If we want to load
63
         * an existing spatial index file, overwrite must be 'false'
64
         * @param fileName name of the rtree spatial index file
65
         * @throws IndexException
66
         */
67
        public RTreeSptLib(IndexParameters params) throws IndexException {
68
                super(params);
69
                try {                        
70
                        //this.rtreeFile = getName();
71
                        PropertySet ps = new PropertySet();
72

    
73
                        // overwrite the file if it exists.
74
                        Boolean b = new Boolean(isOverwrite());
75
                        ps.setProperty("Overwrite", b);
76

    
77
                        // .idx and .dat extensions will be added.
78
                        ps.setProperty("FileName", getName());
79

    
80
                        Integer i = new Integer(defaultPageSize);
81
                        ps.setProperty("PageSize", i);
82
                        diskfile = new DiskStorageManager(ps);
83
                        load();
84
                } catch (SecurityException e) {
85
                        throw new IndexException(e);
86
                } catch (FileNotFoundException e) {
87
                        throw new IndexException(e);
88
                } catch (IOException e) {
89
                        throw new IndexException(e);
90
                }
91
        }
92
        
93
        private void initialize() {
94
                //this.rtreeFile = getName();
95
                PropertySet ps = new PropertySet();
96

    
97
                // overwrite the file if it exists.
98
                Boolean b = new Boolean(isOverwrite());
99
                ps.setProperty("Overwrite", b);
100

    
101
                // .idx and .dat extensions will be added.
102
                ps.setProperty("FileName", getName());
103

    
104
                Integer i = new Integer(defaultPageSize);
105
                ps.setProperty("PageSize", i);
106
                diskfile = new DiskStorageManager(ps);
107
                load();
108
        }
109

    
110
        /**
111
         * If the spatial index file exists and has content
112
         */
113
        public boolean exists(){
114
                return (new File(getName() + ".dat").length() != 0);
115
        }
116

    
117

    
118
        class RTreeVisitor implements IVisitor{
119
                ArrayList solution = new ArrayList();
120
                public void visitNode(INode n) {
121
                }
122
                public void visitData(IData d) {
123
                        solution.add(new Integer(d.getIdentifier()));
124
                }
125
                public List getSolution(){
126
                        return solution;
127
                }
128
        }
129

    
130

    
131
        public List query(Envelope env) {
132
                List solution = null;
133
                Region region = createRegion(env);
134
                RTreeVisitor visitor = new RTreeVisitor();
135
                rtree.intersectionQuery(region,visitor);
136
                solution = visitor.getSolution();
137
                return solution;
138
        }
139

    
140
        public List containtmentQuery(Envelope env) {
141
                List solution = null;
142
                Region region = createRegion(env);
143
                RTreeVisitor visitor = new RTreeVisitor();
144
                rtree.containmentQuery(region,visitor);
145
                solution = visitor.getSolution();
146
                return solution;
147
        }
148

    
149
        /**
150
         * Warn! This RTree implemention doesnt care if 'index'
151
         * entry has been indexed yet
152
         */
153
        public void insert(Envelope env, int index) {
154
                rtree.insertData(null, createRegion(env), index);
155
        }
156

    
157
        private Region createRegion(Envelope env){
158
                return new Region(env.getLowerCorner(), env.getUpperCorner());
159
        }
160

    
161
        public void delete(Envelope env, int index) {
162
                rtree.deleteData(createRegion(env), index);
163
        }
164

    
165
        /**
166
         * Looks for N indexes nearest to the specified rect.
167
         * @param numberOfNearest
168
         * @param rect
169
         * @return
170
         */
171
        public List findNNearest(int numberOfNearest, Envelope env) {
172
                List solution = null;
173
                Region region = createRegion(env);
174
                RTreeVisitor visitor = new RTreeVisitor();
175
                rtree.nearestNeighborQuery(numberOfNearest, region,visitor);
176
                solution = visitor.getSolution();
177
                return solution;
178
        }
179

    
180
        /**
181
         * Looks for the N indexes nearest to the specified point
182
         * @param numberOfNearest
183
         * @param point
184
         * @return
185
         */
186
        public List findNNearest(int numberOfNearest, Point2D point) {
187
                List solution = null;
188
                spatialindex.spatialindex.Point sptPoint = new
189
                        spatialindex.spatialindex.Point(new double[]{point.getX(), point.getY()});
190
                RTreeVisitor visitor = new RTreeVisitor();
191
                rtree.nearestNeighborQuery(numberOfNearest, sptPoint,visitor);
192
                solution = visitor.getSolution();
193
                return solution;
194
        }
195

    
196

    
197

    
198
        public void flush(){
199
                rtree.flush();
200
        }
201

    
202
        public void load() {
203
//                 applies a main memory random buffer on top of the persistent
204
                // storage manager
205
                IBuffer buffer = new RandomEvictionsBuffer(diskfile, BUFFER_SIZE, false);
206

    
207
                // Create a new, empty, RTree with dimensionality 2, minimum load
208
                // 70%, using "file" as
209
                // the StorageManager and the RSTAR splitting policy.
210
                PropertySet ps2 = new PropertySet();
211

    
212
                Double f = new Double(defaultFillFactor);
213
                ps2.setProperty("FillFactor", f);
214

    
215
                Integer i = new Integer(2);
216
                ps2.setProperty("Dimension", i);
217

    
218
                File file = new File(getName() + ".dat");
219
                if(file.length() != 0){
220
                        ps2.setProperty("IndexIdentifier", new Integer(1));
221
                }
222
                rtree = new RTree(ps2, buffer);
223
        }
224
        
225
        public void load(File f) throws IndexException {
226
                load();
227
        }
228
        
229
        public void flush(File f) throws IndexException {
230
                flush();
231
        }
232

    
233
        public void close() {
234
        }
235

    
236
        public File getFile() {
237
                return new File(getName() + ".dat");
238
        }
239

    
240
        public void clear() {
241
                this.rtree = new RTree();
242
        }
243
}