00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #ifndef __STRINGPOOL_HPP
00023 #define __STRINGPOOL_HPP
00024
00025 #include <xqilla/framework/XQillaExport.hpp>
00026 #include <xercesc/framework/MemoryManager.hpp>
00027 #include <memory>
00028 #include <cstring>
00029
00030 #include <string>
00031
00032 class XQILLA_API StringPool
00033 {
00034 public:
00035 StringPool(XERCES_CPP_NAMESPACE_QUALIFIER MemoryManager *mm);
00036 ~StringPool();
00037
00039 const XMLCh* getPooledString(const XMLCh *src);
00041 const XMLCh* getPooledString(const XMLCh *src, unsigned int length);
00043 const XMLCh* getPooledString(const char *src);
00044
00045 unsigned int getCount() const { return _count; }
00046 unsigned int getHits() const { return _hits; }
00047 unsigned int getMisses() const { return _misses; }
00048 unsigned int getTooBig() const { return _toobig; }
00049 void dumpStatistics() const;
00050
00051 private:
00052 StringPool(const StringPool&);
00053 StringPool &operator=(const StringPool&);
00054
00055 static unsigned int hash(const XMLCh *v, unsigned int length);
00056 const XMLCh *replicate(const XMLCh *v, unsigned int length) const;
00057 void resize();
00058
00059 class Bucket
00060 {
00061 public:
00062 Bucket(const XMLCh *v, unsigned int l, unsigned int h, Bucket *n)
00063 : value(v), length(l), hashValue(h), next(n) {}
00064
00065 const XMLCh *value;
00066 unsigned int length;
00067 unsigned int hashValue;
00068 Bucket *next;
00069 };
00070
00071 XERCES_CPP_NAMESPACE_QUALIFIER MemoryManager *_mm;
00072 Bucket **_bucketList;
00073 unsigned int _modulus;
00074 unsigned int _count;
00075 unsigned int _hits;
00076 unsigned int _misses;
00077 unsigned int _toobig;
00078 };
00079
00080 inline unsigned int StringPool::hash(const XMLCh *v, unsigned int length)
00081 {
00082 unsigned int hashVal = 0;
00083 while(length) {
00084 hashVal += (hashVal * 37) + (hashVal >> 24) + (unsigned int)(*v);
00085 ++v;
00086 --length;
00087 }
00088 return hashVal;
00089 }
00090
00091 inline const XMLCh *StringPool::replicate(const XMLCh *v, unsigned int length) const
00092 {
00093 unsigned int size = length * sizeof(XMLCh);
00094 XMLCh *ret = (XMLCh*)_mm->allocate(size + sizeof(XMLCh));
00095 memcpy(ret, v, size);
00096 ret[length] = 0;
00097 return ret;
00098 }
00099
00100 #endif