Add iterators for child traversal.

llvm-svn: 45246
This commit is contained in:
Anton Korobeynikov 2007-12-20 01:21:50 +00:00
parent 65c001e6bc
commit 5ab614824d
1 changed files with 29 additions and 13 deletions

View File

@ -34,8 +34,13 @@ class Trie {
public: public:
class Node { class Node {
friend class Trie; friend class Trie;
friend class GraphTraits<Trie<Payload> >;
public:
typedef std::vector<Node*> NodeVectorType;
typedef typename NodeVectorType::iterator iterator;
typedef typename NodeVectorType::const_iterator const_iterator;
private:
typedef enum { typedef enum {
Same = -3, Same = -3,
StringIsPrefix = -2, StringIsPrefix = -2,
@ -43,8 +48,6 @@ public:
DontMatch = 0, DontMatch = 0,
HaveCommonPart HaveCommonPart
} QueryResult; } QueryResult;
typedef std::vector<Node*> NodeVector;
typedef typename std::vector<Node*>::iterator NodeVectorIter;
struct NodeCmp { struct NodeCmp {
bool operator() (Node* N1, Node* N2) { bool operator() (Node* N1, Node* N2) {
@ -57,7 +60,7 @@ public:
std::string Label; std::string Label;
Payload Data; Payload Data;
NodeVector Children; NodeVectorType Children;
// Do not implement // Do not implement
Node(const Node&); Node(const Node&);
@ -67,7 +70,7 @@ public:
if (Children.empty()) if (Children.empty())
Children.push_back(N); Children.push_back(N);
else { else {
NodeVectorIter I = std::lower_bound(Children.begin(), Children.end(), iterator I = std::lower_bound(Children.begin(), Children.end(),
N, NodeCmp()); N, NodeCmp());
// FIXME: no dups are allowed // FIXME: no dups are allowed
Children.insert(I, N); Children.insert(I, N);
@ -76,7 +79,7 @@ public:
inline void setEdge(Node* N) { inline void setEdge(Node* N) {
char Id = N->Label[0]; char Id = N->Label[0];
NodeVectorIter I = std::lower_bound(Children.begin(), Children.end(), iterator I = std::lower_bound(Children.begin(), Children.end(),
Id, NodeCmp()); Id, NodeCmp());
assert(I != Children.end() && "Node does not exists!"); assert(I != Children.end() && "Node does not exists!");
*I = N; *I = N;
@ -119,20 +122,33 @@ public:
<< "Label: " << Label << "\n" << "Label: " << Label << "\n"
<< "Children:\n"; << "Children:\n";
for (NodeVectorIter I = Children.begin(), E = Children.end(); I != E; ++I) for (iterator I = Children.begin(), E = Children.end(); I != E; ++I)
std::cerr << (*I)->Label << "\n"; std::cerr << (*I)->Label << "\n";
} }
#endif #endif
inline Node* getEdge(char Id) { inline Node* getEdge(char Id) {
Node* fNode = NULL; Node* fNode = NULL;
NodeVectorIter I = std::lower_bound(Children.begin(), Children.end(), iterator I = std::lower_bound(Children.begin(), Children.end(),
Id, NodeCmp()); Id, NodeCmp());
if (I != Children.end() && (*I)->Label[0] == Id) if (I != Children.end() && (*I)->Label[0] == Id)
fNode = *I; fNode = *I;
return fNode; return fNode;
} }
inline iterator begin() { return Children.begin(); }
inline const_iterator begin() const { return Children.begin(); }
inline iterator end () { return Children.end(); }
inline const_iterator end () const { return Children.end(); }
inline size_t size () const { return Children.size(); }
inline bool empty() const { return Children.empty(); }
inline const Node* &front() const { return Children.front(); }
inline Node* &front() { return Children.front(); }
inline const Node* &back() const { return Children.back(); }
inline Node* &back() { return Children.back(); }
}; };
private: private:
@ -260,17 +276,17 @@ const Payload& Trie<Payload>::lookup(const std::string& s) const {
template<class Payload> template<class Payload>
struct GraphTraits<Trie<Payload> > { struct GraphTraits<Trie<Payload> > {
typedef typename Trie<Payload>::Node NodeType; typedef typename Trie<Payload>::Node NodeType;
typedef typename std::vector<NodeType*>::iterator ChildIteratorType; typedef typename Trie<Payload>::Node::iterator ChildIteratorType;
static inline NodeType *getEntryNode(const Trie<Payload>& T) { static inline NodeType *getEntryNode(const Trie<Payload>& T) {
return T.getRoot(); return T.getRoot();
} }
static inline ChildIteratorType child_begin(NodeType *N) { static inline ChildIteratorType child_begin(NodeType *N) {
return N->Children.begin(); return N->begin();
} }
static inline ChildIteratorType child_end(NodeType *N) { static inline ChildIteratorType child_end(NodeType *N) {
return N->Children.end(); return N->end();
} }
typedef typename std::vector<NodeType*>::const_iterator nodes_iterator; typedef typename std::vector<NodeType*>::const_iterator nodes_iterator;