VR-Forces 4.7 Class Documentation
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Groups Pages
indexChooserFeatureSet.h
Go to the documentation of this file.
1 /******************************************************************************
2  * Copyright (c) 2015 MAK Technologies, Inc.
3  * All rights reserved.
4  ******************************************************************************/
5 
9 
10 #pragma once
11 
14 
15 namespace MAKVRinTerra
16 {
17  template <typename FS>
18  class DtIndexChooserFeatureSet : public FS
19  {
20  public:
21  typedef typename FS::Feature Feature;
22  typedef typename FS::ForEachFunction ForEachFunction;
23  typedef typename FS::LoadedCallback LoadedCallback;
24  typedef typename FS::DetachCallback DetachCallback;
25 
26  typedef boost::shared_ptr<DtIndexChooserFeatureSet> Ptr;
27 
28  static FS* Make(FS* input, FS* mainIndex)
29  {
30  return new DtIndexChooserFeatureSet(input, mainIndex);
31  }
32 
33  std::string label() const { return myInput->label() + " index chooser"; }
34 
35  unsigned numberOfFeatures() const
36  {
37  unsigned tot = myMainIndex->numberOfFeatures();
38 
39  Mutex::scoped_lock lock(myData->myMutex, false);
40  for (typename Data::const_iterator i=myData->begin(), end=myData->end(); i!=end; ++i)
41  tot += i->second->numberOfFeatures();
42 
43  return tot;
44  }
45 
46  bool elided() const
47  {
48  if (!myMainIndex->elided())
49  return false;
50 
51  Mutex::scoped_lock lock(myData->myMutex, false);
52  for (typename Data::const_iterator i=myData->begin(), end=myData->end(); i!=end; ++i)
53  if (!i->second->elided())
54  return false;
55 
56  return true;
57  }
58 
59  bool empty() const
60  {
61  if (!myMainIndex->empty())
62  return false;
63 
64  Mutex::scoped_lock lock(myData->myMutex, false);
65  for (typename Data::const_iterator i=myData->begin(), end=myData->end(); i!=end; ++i)
66  if (!i->second->empty())
67  return false;
68 
69  return true;
70  }
71 
72  bool isIndexed() const
73  {
74  return true;
75  }
76 
77  bool isCacheable(const boost::optional<DtFeatureGeometry>& area) const
78  {
79  return myMainIndex->isCacheable(area);
80  }
81 
82  void cacheEstimate(double& time, double& size, const boost::optional<DtFeatureGeometry>& area) const
83  {
84  myMainIndex->cacheEstimate(time, size, area);
85  }
86 
87  void cacheData(
88  const boost::optional<DtFeatureGeometry>& area,
89  DtFeatureCacheProgressCallback* progress) const
90  {
91  myMainIndex->cacheData(area, progress);
92  }
93 
94  bool loaded(double timeout=0.0) const
95  {
96  tbb::tick_count start = tbb::tick_count::now();
97 
98  if (!myMainIndex->loaded(timeout))
99  return false;
100 
101  Mutex::scoped_lock lock(myData->myMutex, false);
102  for (typename Data::const_iterator i=myData->begin(), end=myData->end(); i!=end; ++i)
103  {
104  double whatsleft = timeout - (tbb::tick_count::now() - start).seconds();
105  if (whatsleft < 0)
106  whatsleft = 0;
107 
108  if (!i->second->loaded(whatsleft))
109  return false;
110  }
111 
112  return true;
113  }
114 
115  FS* clone() const
116  {
117  return new DtIndexChooserFeatureSet(*this);
118  }
119 
121  {
122  return myMainIndex->addLoadedCallback(cb);
123  }
124 
125  struct Caller
126  {
127  void operator()(const Feature& feature) const
128  {
129  if (query.matches(feature))
130  func(feature);
131  }
132 
134  : func(func), query(query)
135  {
136  }
137 
138  private:
141  };
142 
143  void forEachFeatureParallel(const ForEachFunction& func) const
144  {
145  Caller caller(func, myFilteredAttributes);
146  myMainIndex->forEachFeatureParallel(caller);
147  }
148 
150  {
151  Caller caller(func, myFilteredAttributes);
152  return myMainIndex->forEachFeatureAsync(caller);
153  }
154 
155  FS* filter(
156  const DtQuery& query,
157  const boost::optional<DtFeatureGeometry>& geometry,
158  DtLoadType load) const
159  {
160  DtQuery combined = myFilteredAttributes && query;
161 
163  if (geometry)
164  return myMainIndex->filter(combined, geometry, load);
165 
168  if (!query.isTrue())
169  {
170  std::auto_ptr<FS> filterTest(myInput->filter(combined, geometry, DO_NOT_LOAD));
171  if (DtIsElided(filterTest.get()))
172  return 0;
173  }
174 
179  if (load == DO_NOT_LOAD)
180  return new DtIndexChooserFeatureSet(*this, combined);
181 
182  DtWarn << "Query = " << query << std::endl;
183  DtWarn << "Previous query = " << myFilteredAttributes << std::endl;
184  DtWarn << "Combined = " << combined << std::endl;
185 
188  if (const DtHasAttribute* attr = query.trycast<DtHasAttribute>())
189  {
190  Mutex::scoped_lock lock(myData->myMutex, true);
191  typename Data::const_iterator i = myData->myIndexMap.find(attr->key());
192  if (i != myData->myIndexMap.end())
193  {
194  DtInfo << "Using feature attribute index on key " << attr->key() << std::endl;
195  return i->second->filter(combined, geometry, load);
196  }
197 
198  typedef DtAttributeIndexingFeatureSet<FS> AttributeIndex;
199  typedef typename AttributeIndex::Config AttributeConfig;
200 
201  std::auto_ptr<FS> set(AttributeIndex::Make(
202  new AttributeConfig(myInput->filter(true, LOAD), attr->key())));
203 
204  DtInfo << "Creating feature attribute index on key " << attr->key() << std::endl;
205  std::auto_ptr<FS> ret(set->filter(combined, geometry, load));
206 
207  myData->myIndexMap.insert(attr->key(), set.release());
208  return ret.release();
209  }
210 
211  return myMainIndex->filter(combined, geometry, load);
212  }
213 
214  private:
215  explicit DtIndexChooserFeatureSet(FS* input, FS* mainIndex)
216  : myInput(input)
217  , myMainIndex(mainIndex)
218  , myData(new Data())
219  , myFilteredAttributes(true)
220  {
221  }
222 
224  const DtIndexChooserFeatureSet& from, const DtQuery& combined)
225  : myInput(from.myInput)
226  , myMainIndex(from.myMainIndex)
227  , myData(from.myData)
228  , myFilteredAttributes(combined)
229  {
230  }
231 
233  : myInput(from.myInput)
234  , myMainIndex(from.myMainIndex)
235  , myData(from.myData)
237  {
238  }
239 
240  typedef tbb::queuing_rw_mutex Mutex;
241 
242  const boost::shared_ptr<FS> myInput;
243  const boost::shared_ptr<FS> myMainIndex;
244 
245  struct Data
246  {
247  typedef boost::ptr_map<const DtFeature::Key, FS> Map;
248  typedef typename Map::const_iterator const_iterator;
249 
250  const_iterator begin() const { return myIndexMap.begin(); }
251  const_iterator end() const { return myIndexMap.end(); }
252 
253  mutable Mutex myMutex;
255  };
256 
257  const boost::shared_ptr<Data> myData;
259  };
260 }

Document ID: Generated on Fri Apr 26 21:53:14 EDT 2019 from SVN revision 197883
Copyright © 2005-2019 VT MAK. All Rights Reserved (www.mak.com)