SmartHierarchy.h

Go to the documentation of this file.
00001 #ifndef TAGCOLL_SMARTHIERARCHY_H
00002 #define TAGCOLL_SMARTHIERARCHY_H
00003 
00008 /* 
00009  * Copyright (C) 2003--2006  Enrico Zini <enrico@debian.org>
00010  *
00011  * This library is free software; you can redistribute it and/or
00012  * modify it under the terms of the GNU Lesser General Public
00013  * License as published by the Free Software Foundation; either
00014  * version 2.1 of the License, or (at your option) any later version.
00015  *
00016  * This library is distributed in the hope that it will be useful,
00017  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00018  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00019  * Lesser General Public License for more details.
00020  *
00021  * You should have received a copy of the GNU Lesser General Public
00022  * License along with this library; if not, write to the Free Software
00023  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307  USA
00024  */
00025 
00026 #include <tagcoll/coll/base.h>
00027 #include <vector>
00028 #include <set>
00029 #include <string>
00030 
00031 namespace tagcoll
00032 {
00033 
00034 // Base class for the auto-expanding tree nodes
00035 template<typename COLL>
00036 class HierarchyNode
00037 {
00038 protected:
00039     typedef typename coll::coll_traits<COLL>::item_type ITEM;
00040     typedef typename coll::coll_traits<COLL>::tag_type TAG;
00041     typedef typename coll::coll_traits<COLL>::itemset_type ITEMSET;
00042     typedef typename coll::coll_traits<COLL>::tagset_type TAGSET;
00043 
00044     // Tag name
00045     TAG _tag;
00046     COLL* coll;
00047     std::vector<HierarchyNode<COLL>*> children;
00048     ITEMSET items;
00049     HierarchyNode<COLL>* _parent;
00050 
00051 public:
00052     HierarchyNode(const TAG& tag, const COLL& coll)
00053         : _tag(tag), coll(new COLL(coll)), _parent(0) {}
00054     HierarchyNode(HierarchyNode<COLL>* parent, const TAG& tag, const COLL& coll)
00055         : _tag(tag), coll(new COLL(coll)), _parent(parent) {}
00056     virtual ~HierarchyNode();
00057 
00058     typedef typename std::vector<HierarchyNode<COLL>*>::iterator iterator;
00059 
00060     // Get the node tag (const version)
00061     const TAG& tag() const { return _tag; }
00062 
00063     // Get the node tag
00064     TAG tag() { return _tag; }
00065 
00066     // Get the parent of this node (0 if it is the root node)
00067     HierarchyNode<COLL>* parent() const { return _parent; }
00068 
00069     // Expand the collection in the children of this node
00070     virtual void expand() = 0;
00071 
00072     // Get the number of child nodes
00073     int size()
00074     {
00075         if (coll)
00076             expand();
00077         return children.size();
00078     }
00079 
00080     iterator begin()
00081     {
00082         if (coll)
00083             expand();
00084         return children.begin();
00085     }
00086 
00087     iterator end()
00088     {
00089         if (coll)
00090             expand();
00091         return children.end();
00092     }
00093 
00094     // Get a child node by index
00095     HierarchyNode<COLL>* operator[](int idx)
00096     {
00097         if (coll)
00098             expand();
00099         return children[idx];
00100     }
00101 
00102     // Get the set of items present in this node
00103     const std::set<ITEM>& getItems()
00104     {
00105         if (coll)
00106             expand();
00107         return items;
00108     }
00109 };
00110 
00111 // Hierarchy of items where information is replicated to acheive intuitive
00112 // navigability of the resulting structure
00113 template<typename COLL>
00114 class SmartHierarchyNode : public HierarchyNode<COLL>
00115 {
00116 protected:
00117     typedef typename HierarchyNode<COLL>::ITEM ITEM;
00118     typedef typename HierarchyNode<COLL>::TAG TAG;
00119     typedef typename HierarchyNode<COLL>::ITEMSET ITEMSET;
00120     typedef typename HierarchyNode<COLL>::TAGSET TAGSET;
00121 
00122     typename HierarchyNode<COLL>::ITEMSET unexpandedItems;
00123 
00124     // Threshold of child items below which the child hierarchy is flattened
00125     // and they all become children of this node
00126     int flattenThreshold;
00127     
00128     // Expand the collection in the children of this node
00129     virtual void expand();
00130 
00131 public:
00132     SmartHierarchyNode(const TAG& tag, const COLL& coll, int flattenThreshold = 0)
00133         throw () :
00134             HierarchyNode<COLL>(tag, coll),
00135             flattenThreshold(flattenThreshold) {}
00136 
00137     SmartHierarchyNode(
00138             HierarchyNode<COLL>* parent,
00139             const TAG& tag,
00140             const COLL& coll,
00141             int flattenThreshold = 0)
00142         throw () :
00143             HierarchyNode<COLL>(parent, tag, coll),
00144             flattenThreshold(flattenThreshold)
00145         {
00146             std::set<TAG> tags; tags.insert(tag);
00147             unexpandedItems = coll.getItemsExactMatch(tags);
00148         }
00149 
00150     virtual ~SmartHierarchyNode() {}
00151 };
00152 
00153 template<typename COLL>
00154 inline HierarchyNode<COLL>* smartHierarchyNode(const typename coll::coll_traits<COLL>::tag_type& tag, const COLL& coll, int flattenThreshold)
00155 {
00156     return new SmartHierarchyNode<COLL>(tag, coll, flattenThreshold);
00157 }
00158 template<typename COLL>
00159 inline HierarchyNode<COLL>* smartHierarchyNode(HierarchyNode<COLL>* parent, const typename coll::coll_traits<COLL>::tag_type& tag, const COLL& coll, int flattenThreshold)
00160 {
00161     return new SmartHierarchyNode<COLL>(parent, tag, coll, flattenThreshold);
00162 }
00163 
00164 template<typename TAG>
00165 TAG mergeTags(const TAG& tag1, const TAG& tag2)
00166 {
00167     return tag1;
00168 }
00169 
00170 template<>
00171 std::string mergeTags(const std::string& tag1, const std::string& tag2);
00172 
00173 
00174 // SmartHierarchyNode which also does merging of equivalent tags
00175 template<typename COLL>
00176 class CleanSmartHierarchyNode : public SmartHierarchyNode<COLL>
00177 {
00178 protected:
00179     typedef typename SmartHierarchyNode<COLL>::ITEM ITEM;
00180     typedef typename SmartHierarchyNode<COLL>::TAG TAG;
00181     typedef typename SmartHierarchyNode<COLL>::ITEMSET ITEMSET;
00182     typedef typename SmartHierarchyNode<COLL>::TAGSET TAGSET;
00183 
00184     // Expand the collection in the children of this node
00185     virtual void expand();
00186 
00187     TAG setTag(const TAG& tag) { return this->_tag = tag; }
00188     HierarchyNode<COLL>* setParent(HierarchyNode<COLL>* parent) { return this->_parent = parent; }
00189 
00190 public:
00191     CleanSmartHierarchyNode(const TAG& tag, const COLL& coll, int flattenThreshold = 0)
00192         : SmartHierarchyNode<COLL>(tag, coll, flattenThreshold) {}
00193     CleanSmartHierarchyNode(HierarchyNode<COLL>* parent, const TAG& tag, const COLL& coll, int flattenThreshold = 0)
00194         : SmartHierarchyNode<COLL>(parent, tag, coll, flattenThreshold) {}
00195     virtual ~CleanSmartHierarchyNode() {}
00196 };
00197 
00198 template<typename COLL>
00199 inline HierarchyNode<COLL>* cleanSmartHierarchyNode(const typename coll::coll_traits<COLL>::tag_type& tag, const COLL& coll, int flattenThreshold)
00200 {
00201     return new CleanSmartHierarchyNode<COLL>(tag, coll, flattenThreshold);
00202 }
00203 template<typename COLL>
00204 inline HierarchyNode<COLL>* cleanSmartHierarchyNode(HierarchyNode<COLL>* parent, const typename coll::coll_traits<COLL>::tag_type& tag, const COLL& coll, int flattenThreshold)
00205 {
00206     return new CleanSmartHierarchyNode<COLL>(parent, tag, coll, flattenThreshold);
00207 }
00208 
00209 }
00210 
00211 // vim:set ts=4 sw=4:
00212 #endif

Generated on Fri Feb 8 10:50:41 2008 for libtagcoll by  doxygen 1.5.4