Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | Directories | File List | Namespace Members | Class Members | File Members

name.h

Go to the documentation of this file.
00001 //
00002 // C++ Interface: name
00003 //
00004 // Description:
00005 //
00006 //
00007 // Author: Toti <root@totibox>, (C) 2005
00008 //
00009 // Copyright: See COPYING file that comes with this distribution
00010 //
00011 //
00012 
00013 #ifndef _NAME_H_
00014 #define _NAME_H_
00015 
00016 #include <string>
00017 #include <iostream>
00018 #include <map>
00019 #include <vector>
00020 #include <celutil/basictypes.h>
00021 #include <celutil/debug.h>
00022 #include <celutil/util.h>
00023 #include <celutil/utf8.h>
00024 
00025 // TODO: this can be "detemplatized" by creating e.g. a global-scope enum InvalidCatalogNumber since there
00026 // lies the one and only need for type genericity.
00027 template <class OBJ> class NameDatabase
00028 {
00029  public:
00030     typedef std::map<std::string, uint32, CompareIgnoringCasePredicate> NameIndex;
00031     typedef std::multimap<uint32, std::string> NumberIndex;
00032 
00033  public:
00034     NameDatabase() {};
00035 
00036 
00037     uint32 getNameCount() const;
00038 
00039     void add(const uint32, const std::string&);
00040 
00041     // delete all names associated with the specified catalog number
00042     void erase(const uint32);
00043 
00044     uint32      getCatalogNumberByName(const std::string&) const;
00045     std::string getNameByCatalogNumber(const uint32)       const;
00046 
00047     NumberIndex::const_iterator getFirstNameIter(const uint32 catalogNumber) const;
00048     NumberIndex::const_iterator getFinalNameIter() const;
00049 
00050     std::vector<std::string> getCompletion(const std::string& name) const;
00051 
00052  protected:
00053     NameIndex   nameIndex;
00054     NumberIndex numberIndex;
00055 };
00056 
00057 
00058 
00059 template <class OBJ>
00060 uint32 NameDatabase<OBJ>::getNameCount() const
00061 {
00062     return nameIndex.size();
00063 }
00064 
00065 
00066 template <class OBJ>
00067 void NameDatabase<OBJ>::add(const uint32 catalogNumber, const std::string& name)
00068 {
00069     if (name.length() != 0)
00070     {
00071 #ifdef DEBUG
00072         uint32 tmp;
00073         if ((tmp = getCatalogNumberByName(name)) != OBJ::InvalidCatalogNumber)
00074             DPRINTF(2,"Duplicated name '%s' on object with catalog numbers: %d and %d\n", name.c_str(), tmp, catalogNumber);
00075 #endif
00076         // Add the new name
00077         //nameIndex.insert(NameIndex::value_type(name, catalogNumber));
00078 
00079         nameIndex[name]   = catalogNumber;
00080         numberIndex.insert(NumberIndex::value_type(catalogNumber, name));
00081     }
00082 }
00083 
00084 
00085 template <class OBJ>
00086 void NameDatabase<OBJ>::erase(const uint32 catalogNumber)
00087 {
00088     numberIndex.erase(catalogNumber);
00089 }
00090 
00091 
00092 template <class OBJ>
00093 uint32 NameDatabase<OBJ>::getCatalogNumberByName(const std::string& name) const
00094 {
00095     NameIndex::const_iterator iter = nameIndex.find(name);
00096 
00097     if (iter == nameIndex.end())
00098         return OBJ::InvalidCatalogNumber;
00099     else
00100         return iter->second;
00101 }
00102 
00103 
00104 // Return the first name matching the catalog number or end()
00105 // if there are no matching names.  The first name *should* be the
00106 // proper name of the OBJ, if one exists. This requires the
00107 // OBJ name database file to have the proper names listed before
00108 // other designations.  Also, the STL implementation must
00109 // preserve this order when inserting the names into the multimap
00110 // (not certain whether or not this behavior is in the STL spec.
00111 // but it works on the implementations I've tried so far.)
00112 template <class OBJ>
00113 std::string NameDatabase<OBJ>::getNameByCatalogNumber(const uint32 catalogNumber) const
00114 {
00115    if (catalogNumber == OBJ::InvalidCatalogNumber)
00116         return "";
00117 
00118    NumberIndex::const_iterator iter   = numberIndex.lower_bound(catalogNumber);
00119 
00120    if (iter != numberIndex.end() && iter->first == catalogNumber)
00121        return iter->second;
00122 }
00123 
00124 
00125 // Return the first name matching the catalog number or end()
00126 // if there are no matching names.  The first name *should* be the
00127 // proper name of the OBJ, if one exists. This requires the
00128 // OBJ name database file to have the proper names listed before
00129 // other designations.  Also, the STL implementation must
00130 // preserve this order when inserting the names into the multimap
00131 // (not certain whether or not this behavior is in the STL spec.
00132 // but it works on the implementations I've tried so far.)
00133 template <class OBJ>
00134 NameDatabase<OBJ>::NumberIndex::const_iterator NameDatabase<OBJ>::getFirstNameIter(const uint32 catalogNumber) const
00135 {
00136     NumberIndex::const_iterator iter   = numberIndex.lower_bound(catalogNumber);
00137 
00138     if (iter == numberIndex.end() || iter->first != catalogNumber)
00139         return getFinalNameIter();
00140     else
00141         return iter;
00142 }
00143 
00144 
00145 template <class OBJ>
00146 NameDatabase<OBJ>::NumberIndex::const_iterator NameDatabase<OBJ>::getFinalNameIter() const
00147 {
00148     return numberIndex.end();
00149 }
00150 
00151 
00152 template <class OBJ>
00153 std::vector<std::string> NameDatabase<OBJ>::getCompletion(const std::string& name) const
00154 {
00155     std::vector<std::string> completion;
00156     for (NameIndex::const_iterator iter = nameIndex.begin(); iter != nameIndex.end(); ++iter)
00157     {
00158         if (!UTF8StringCompare(iter->first, name, name.length()))
00159         {
00160             completion.push_back(iter->first);
00161         }
00162     }
00163     return completion;
00164 }
00165 
00166 #endif  // _NAME_H_

Generated on Sat Jan 14 22:30:28 2006 for Celestia by  doxygen 1.4.1