8#ifndef FMToutputnodecache_H
9#define FMToutputnodecache_H
13#include <unordered_map>
15#include <boost/serialization/serialization.hpp>
16#include <boost/serialization/map.hpp>
17#include <boost/serialization/vector.hpp>
20#include "FMTGraph.hpp"
32 template <
class tvdescriptor,
class titerator>
66 m_inmemorynodes(initialnodes), m_beginit(nullptr), m_endit(nullptr), m_searchtree(), m_allocator(), m_reserve()
68 m_inmemorynodes.shrink_to_fit();
69 std::sort(m_inmemorynodes.begin(),m_inmemorynodes.end());
79 FMTOutputNodeCache(
const titerator& first,
const titerator& last,std::allocator<tvdescriptor>& p_allocator,
const size_t& p_reserve) :
80 m_inmemorynodes(), m_beginit(&first), m_endit(&last), m_searchtree(),m_allocator(&p_allocator), m_reserve(p_reserve)
84 std::vector<tvdescriptor>allocated(*m_allocator);
85 allocated.reserve(m_reserve);
86 for (titerator it = *m_beginit; it != *m_endit; ++it)
88 allocated.push_back(*it);
92 std::sort(allocated.begin(), allocated.end());
93 allocated.shrink_to_fit();
94 m_inmemorynodes.swap(allocated);
105 m_searchtree.erase(node.
source);
116 return m_searchtree.find(node.
source) != m_searchtree.end();
126 size_t largestsize = 0;
127 unsigned long long removedmemory = 0;
128 notecacheit largestiterator = m_searchtree.end();
129 for (
typename std::map<
Core::FMTOutputSource, std::vector<tvdescriptor>>::iterator mapit = m_searchtree.begin(); mapit != m_searchtree.end(); mapit++)
131 size_t sizeofvec = mapit->second.size();
132 if (sizeofvec > largestsize)
134 largestsize = mapit->second.size();
135 largestiterator = mapit;
139 if (largestiterator != m_searchtree.end())
141 removedmemory = largestsize *
sizeof(tvdescriptor);
142 m_searchtree.erase(largestiterator);
144 return removedmemory;
156 const std::vector<Core::FMTTheme>&themes,
bool& exactvecticies)
const
158 return this->_getCleanDescriptors(targetnode, actions, themes, exactvecticies);
168 m_searchtree[targetnode.
source] = vertices;
169 m_searchtree[targetnode.
source].shrink_to_fit();
179 m_inmemorynodes.clear();
180 m_searchtree.clear();
188 void rebase(
const titerator& beginofdevs,
const titerator& endofdevs)
190 m_beginit = &beginofdevs;
191 m_endit = &endofdevs;
200 if (m_beginit==
nullptr)
202 if (m_inmemorynodes.size() < rhs.m_inmemorynodes.size())
204 m_inmemorynodes = rhs.m_inmemorynodes;
208 m_searchtree.insert(rhs.m_searchtree.begin(), rhs.m_searchtree.end());
218 if (m_beginit!=
nullptr)
220 for (titerator it = *m_beginit; it != *m_endit; ++it)
226 refvecs.push_back(*it);
228 refvecs.shrink_to_fit();
229 std::sort(refvecs.begin(), refvecs.end());
232 refvecs = m_inmemorynodes;
244 template<
class Archive>
245 void serialize(Archive& ar,
const unsigned int version)
247 ar & boost::serialization::make_nvp(
"inmemorynodes", m_inmemorynodes);
248 ar & boost::serialization::make_nvp(
"searchtree", m_searchtree);
250 std::vector<tvdescriptor>m_inmemorynodes;
251 titerator
const * m_beginit;
252 titerator
const * m_endit;
253 mutable std::map<Core::FMTOutputSource,std::vector<tvdescriptor>>m_searchtree;
254 std::allocator<tvdescriptor>* m_allocator;
256 typedef typename std::map<Core::FMTOutputSource,std::vector<tvdescriptor>>::const_iterator notecacheit;
267 const std::vector<tvdescriptor>& _getCleanDescriptors(
const Core::FMTOutputNode& targetnode,
const std::vector<Core::FMTAction>& actions,
268 const std::vector<Core::FMTTheme>&themes,
bool& exactnode)
const
271 bool foundSubset =
false;
272 typename std::map<Core::FMTOutputSource, std::vector<tvdescriptor>>::const_iterator parent = this->_getParentNode(targetnode,
273 actions, exactnode, foundSubset);
276 return parent->second;
279 m_searchtree[targetnode.
source] = std::vector<tvdescriptor>(*m_allocator);
280 std::vector<tvdescriptor>& cleaned = m_searchtree[targetnode.
source];
283 cleaned = parent->second;
285 cleaned.reserve(m_reserve);
288 _getActionRebuild(targetnode, actions, cleaned, exactnode);
291 std::vector<tvdescriptor>toRemove(*m_allocator);
292 bool gotSomething =
false;
294 for (
typename std::map<
Core::FMTOutputSource, std::vector<tvdescriptor>>::const_reverse_iterator sit = m_searchtree.rbegin();
295 sit != m_searchtree.rend(); sit++)
302 toRemove.
reserve(cleaned.size());
304 toRemove.insert(toRemove.end(), sit->second.begin(), sit->second.end());
309 if (!toRemove.empty())
311 std::vector<tvdescriptor>difference(*m_allocator);
312 difference.reserve(cleaned.size());
313 std::sort(toRemove.begin(), toRemove.end());
314 std::set_difference(cleaned.begin(), cleaned.end(),
315 toRemove.begin(), toRemove.end(), std::inserter(difference, difference.begin()));
316 cleaned.swap(difference);
333 const std::vector<Core::FMTAction>& actions,
334 std::vector<tvdescriptor>& cleaned,
335 bool& exactnode)
const
339 if (!actionname.empty() && !aggregatesptr.empty())
341 std::map<std::string, std::vector< notecacheit>>potentials;
344 potentials[attributeptr->getName()] = std::vector< notecacheit>();
345 potentials[attributeptr->getName()].reserve(m_reserve);
347 for (notecacheit sit = m_searchtree.begin();
348 sit != m_searchtree.end(); sit++)
350 if (sit->first.isSubsetOf(targetnode.
source, actions) &&
351 (sit->first != targetnode.
source))
353 const std::string nodeaction = sit->first.getAction();
358 potentials[nodeaction].push_back(sit);
363 if (potentials.at(attributeptr->getName()).empty())
368 typename std::vector< notecacheit>::const_iterator testting = potentials.begin()->second.begin();
369 while (testting != potentials.begin()->second.end())
372 std::vector<tvdescriptor>finalSelection((*testting)->second);
373 size_t insertingdone = 1;
374 for (
const auto& attribute : potentials)
378 for (notecacheit it : potentials.at(attribute.first))
380 if ((*testting)->first.isSameButDifferentAction(it->first))
382 finalSelection.insert(finalSelection.end(), it->second.begin(), it->second.end());
392 if (insertingdone == potentials.size())
394 std::sort(finalSelection.begin(), finalSelection.end());
396 finalSelection.erase(std::unique(finalSelection.begin(), finalSelection.end()),finalSelection.end());
397 if ((*testting)->first.isSameButDifferentAction(targetnode.
source))
400 cleaned = finalSelection;
403 std::vector<tvdescriptor>intersection;
404 std::set_intersection(cleaned.begin(), cleaned.end(),
405 finalSelection.begin(), finalSelection.end(), std::inserter(intersection, intersection.begin()));
406 cleaned = intersection;
425 const std::vector<Core::FMTAction>& m_actions,
426 bool& m_exactNode,
bool m_foundSubset)
const
428 notecacheit parentit = m_searchtree.find(m_targetNode.
source);
429 if (parentit != m_searchtree.end())
434 parentit = m_searchtree.begin();
436 m_foundSubset =
false;
437 while (parentit != m_searchtree.end())
441 m_foundSubset =
true;
446 return m_searchtree.end();
Comparator used to check if an action name (or aggregate) already exists in a std container.
Definition: FMTAction.h:421
std::vector< const FMTAction * > getAllAggregates(const std::vector< FMTAction > &actions, bool aggregateonly=false) const
Return the actions matching the action name, or only the matching aggregates.
List of specifications dictating the operability of a subset of developments to this action.
Definition: FMTAction.h:43
Core class holding, as a boost dynamic bitset, which theme attributes are part of a mask.
Definition: FMTMask.h:96
bool isNotThemesSubset(const FMTMask &rhs, const std::vector< const Core::FMTTheme * > &themes) const
Return true if this mask is not part of rhs based on the sorted themes.
void reserve(size_t p_size)
reserve memory for the boost dynamicbitset.
Node of an output representing a set of developments in the graph, holding a source,...
Definition: FMTOutputNode.h:25
FMTOutputSource source
Definition: FMTOutputNode.h:27
Source of an output holding a mask, a target and values, used to compute an output.
Definition: FMTOutputSource.h:44
const std::string & getAction() const
Return a const reference to the action of the output source.
Definition: FMTOutputSource.h:232
bool isSubsetOf(const FMTOutputSource &rhs, const std::vector< Core::FMTAction > &actions) const
Return true if this output source is a subset of another considering the actions.
const FMTMask & getMask() const
Return a const reference to the mask of the output source.
Definition: FMTOutputSource.h:186
Cache of graph vertices for output nodes, keyed by output source, used to speed up output computation...
Definition: FMTOutputNodeCache.h:34
FMTOutputNodeCache(const FMTOutputNodeCache &rhs)=default
Copy constructor for FMTOutputNodeCache.
const std::vector< tvdescriptor > & getVertices(const Core::FMTOutputNode &targetnode, const std::vector< Core::FMTAction > &actions, const std::vector< Core::FMTTheme > &themes, bool &exactvecticies) const
Return the vertices for a target node, using the cache.
Definition: FMTOutputNodeCache.h:155
FMTOutputNodeCache()=default
Default constructor for FMTOutputNodeCache.
void clear()
Clear the cache.
Definition: FMTOutputNodeCache.h:175
unsigned long long removeLargest()
Remove the largest entry of the cache and return the freed memory.
Definition: FMTOutputNodeCache.h:124
FMTOutputNodeCache & operator=(const FMTOutputNodeCache &rhs)=default
Copy assignment operator for FMTOutputNodeCache.
FMTOutputNodeCache(const titerator &first, const titerator &last, std::allocator< tvdescriptor > &p_allocator, const size_t &p_reserve)
Construct a cache from a range of nodes, an allocator and a reserve size.
Definition: FMTOutputNodeCache.h:79
void _pushToVector(std::vector< tvdescriptor > &refvecs) const
Push the nodes of the cache into a vector.
Definition: FMTOutputNodeCache.h:216
void eraseNode(const Core::FMTOutputNode &node)
Erase a node from the cache.
Definition: FMTOutputNodeCache.h:103
FMTOutputNodeCache(const std::vector< tvdescriptor > &initialnodes)
Construct a cache from an initial set of nodes.
Definition: FMTOutputNodeCache.h:65
friend class boost::serialization::access
Definition: FMTOutputNodeCache.h:236
void setValidVertices(const Core::FMTOutputNode &targetnode, const std::vector< tvdescriptor > &vertices) const
Set the valid vertices for a target node in the cache.
Definition: FMTOutputNodeCache.h:166
void insert(const FMTOutputNodeCache &rhs)
Insert the content of another cache into this cache.
Definition: FMTOutputNodeCache.h:198
~FMTOutputNodeCache()=default
Default destructor for FMTOutputNodeCache.
void rebase(const titerator &beginofdevs, const titerator &endofdevs)
Rebase the cache on a new range of developments.
Definition: FMTOutputNodeCache.h:188
bool contains(const Core::FMTOutputNode &node) const
Return true if the cache contains a node.
Definition: FMTOutputNodeCache.h:114
Definition: FMTAreaParser.h:35