Statistics
| Revision:

root / branches / v2_0_0_prep / libraries / libFMap_dal / src / org / gvsig / fmap / dal / feature / impl / DefaultFeatureIndexes.java @ 24496

History | View | Annotate | Download (5.9 KB)

1
/* gvSIG. Geographic Information System of the Valencian Government
2
*
3
* Copyright (C) 2007-2008 Infrastructures and Transports Department
4
* of the Valencian Government (CIT)
5
*
6
* This program is free software; you can redistribute it and/or
7
* modify it under the terms of the GNU General Public License
8
* as published by the Free Software Foundation; either version 2
9
* of the License, or (at your option) any later version.
10
*
11
* This program is distributed in the hope that it will be useful,
12
* but WITHOUT ANY WARRANTY; without even the implied warranty of
13
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
* GNU General Public License for more details.
15
*
16
* You should have received a copy of the GNU General Public License
17
* along with this program; if not, write to the Free Software
18
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
19
* MA  02110-1301, USA.
20
*
21
*/
22

    
23
/*
24
* AUTHORS (In addition to CIT):
25
* 2008 {{Company}}   {{Task}}
26
*/
27

    
28
package org.gvsig.fmap.dal.feature.impl;
29

    
30
import java.util.ArrayList;
31
import java.util.HashMap;
32
import java.util.Iterator;
33
import java.util.List;
34
import java.util.Map;
35

    
36
import org.gvsig.fmap.dal.exceptions.DataException;
37
import org.gvsig.fmap.dal.feature.FeatureIndex;
38
import org.gvsig.fmap.dal.feature.FeatureIndexes;
39
import org.gvsig.fmap.dal.feature.exceptions.FeatureIndexException;
40
import org.gvsig.fmap.dal.feature.spi.FeatureSetProvider;
41
import org.gvsig.fmap.dal.feature.spi.index.FeatureIndexProviderServices;
42
import org.gvsig.tools.evaluator.Evaluator;
43
import org.gvsig.tools.evaluator.EvaluatorFieldValue;
44

    
45
/**
46
 * This class provides access to a FeatureStore local indexes and also
47
 * decides which index to use given an evaluator containing the filter expression.
48
 * 
49
 * @author jyarza
50
 */ 
51
public class DefaultFeatureIndexes implements FeatureIndexes {
52

    
53
        // Access by index name
54
        private Map names;
55
        // Store to which this belongs
56
        private DefaultFeatureStore store;
57

    
58
        /**
59
         * Creates an empty DataIndexes for the given FeatureStore
60
         *
61
         * @param store
62
         *            FeatureStore to whom this belongs
63
         * @throws DataException
64
         */
65
        public DefaultFeatureIndexes(DefaultFeatureStore store)
66
                        throws DataException {
67
                names = new HashMap();
68
                this.store = store;
69
        }
70

    
71
        /* (non-Javadoc)
72
         * @see org.gvsig.fmap.dal.index.DataIndexes#getDataIndex(java.lang.String)
73
         */
74
        public FeatureIndex getFeatureIndex(String name) {
75
                return (FeatureIndex) names.get(name);
76
        }
77

    
78
        /* (non-Javadoc)
79
         * @see org.gvsig.fmap.dal.index.DataIndexes#addIndex(org.gvsig.fmap.dal.feature.FeatureType, java.lang.String, org.gvsig.fmap.dal.feature.DataIndex)
80
         */
81
        public void addIndex(FeatureIndexProviderServices index) {
82
                // By name
83
                names.put(index.getName(), index);
84
        }
85

    
86
        public Iterator iterator() {
87
                return names.values().iterator();
88
        }
89

    
90
        /**
91
         * Using the given evaluator attributes, choose and use an appropriate index 
92
         * to obtain a FeatureSetProvider. If no index can be applied, then this method returns null
93
         * 
94
         * @param evaluator
95
         * @return FeatureSetProvider or null if could not find any appropriate index.
96
         * 
97
         */
98
        public FeatureSetProvider getFeatureSet(Evaluator evaluator) {
99

    
100
                class ApplyIndex {
101
                        DefaultFeatureIndex index;
102
                        EvaluatorFieldValue[] data;
103

    
104
                        ApplyIndex(DefaultFeatureIndex index, EvaluatorFieldValue[] data) {
105
                                this.index = index;
106
                                this.data = data;
107
                        }
108
                        
109
                        /**
110
                         * Checks whether the index supports the evaluator request
111
                         * @return
112
                         */
113
                        boolean isSupported() {
114
                                switch(data[0].getType()) {
115
                                case EvaluatorFieldValue.MATCH:
116
                                        return index.getFeatureIndexProvider().isMatchSupported();
117
                                case EvaluatorFieldValue.NEAREST:
118
                                        return index.getFeatureIndexProvider().isNearestSupported();
119
                                case EvaluatorFieldValue.RANGE:
120
                                        return index.getFeatureIndexProvider().isRangeSupported();
121
                                default:
122
                                        return false;
123
                                }
124
                        }
125
                        
126
                        /**
127
                         * Applies the index using the evaluator fields
128
                         * @return FeatureSetProvider with the result
129
                         * @throws FeatureIndexException
130
                         */
131
                        FeatureSetProvider apply() throws FeatureIndexException {
132
                                switch (data[0].getType()) {
133
                                case EvaluatorFieldValue.MATCH:
134
                                        return index.getMatchFeatureSet(data[0].getValue());
135
                                case EvaluatorFieldValue.RANGE:
136
                                        return index.getRangeFeatureSet(data[0].getValue1(),
137
                                                        data[0].getValue2());
138
                                case EvaluatorFieldValue.NEAREST:
139
                                        if ((data[0].getTolerance() == -1) || (!isSupported()) ) {
140
                                                return index.getNearestFeatureSet(data[0]
141
                                                                .getCount(), data[0].getValue());
142
                                        } else {
143
                                                return index.getNearestFeatureSet(data[0].getCount(), data[0].getValue(), data[0].getTolerance());
144
                                        }
145
                                }
146
                                return null;
147
                        }
148
                }
149
                
150
                // Select applicable indexes
151
                try {
152
                        List applyIndexes = new ArrayList();
153
                        Iterator indexes = this.iterator();
154
                        while (indexes.hasNext()) {
155
                                DefaultFeatureIndex index = (DefaultFeatureIndex) indexes
156
                                                .next();
157
                                String[] attrs = (String[])index.getAttributeNames().toArray();
158
                                for (int i = 0; i < attrs.length; i++) {
159
                                        String attrname = attrs[i];
160
                                        EvaluatorFieldValue[] values = evaluator
161
                                                        .getFieldValues(attrname);
162
                                        if (values != null) {
163
                                                applyIndexes.add(new ApplyIndex(index, values));
164
                                                break;
165
                                        }
166
                                }
167
                        }
168
                        
169
                        // If there's not any applicable index, return null
170
                        if (applyIndexes.size() == 0) return null;
171
                        
172
                        // Lookup an index with support for the requested function
173
                        Iterator it = applyIndexes.iterator();
174
                        ApplyIndex index = (ApplyIndex) it.next();
175
                        while ( it.hasNext() && (!index.isSupported()) ) {
176
                                index = (ApplyIndex) it.next();
177
                        }
178
                        
179
                        // If there is not any any index supporting the function, use the first one
180
                        if (!index.isSupported()) {
181
                                this.store.getLogger().info("No index support for the evaluator values. Using default index.");
182
                                index = (ApplyIndex) applyIndexes.get(0);
183
                        }
184
                        
185
                        // Apply index
186
                        return index.apply();
187
                        
188
                } catch (Exception e) {
189
                        this.store.getLogger().error("Error searching for an index to apply.",
190
                                        e);
191
                        return null;
192
                }
193
        }
194
}