]> git.saurik.com Git - wxWidgets.git/commitdiff
Fixes for wxHashTable when wxUSE_STL=1:
authorMattia Barbon <mbarbon@cpan.org>
Tue, 19 Aug 2003 21:17:04 +0000 (21:17 +0000)
committerMattia Barbon <mbarbon@cpan.org>
Tue, 19 Aug 2003 21:17:04 +0000 (21:17 +0000)
wxHashTable must work like an hash_multimap, not an hash_map.
wxHashTable::Delete is supposed to actually delete entries
more tests in console sample.

git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@23034 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775

include/wx/hash.h
include/wx/hashmap.h
samples/console/console.cpp

index 0b3470f6d8c716fee021cf14c3da104cacfcf565..3720dd0c1fd0c99246c3e1d932baa2bf42cb1d13 100644 (file)
@@ -140,7 +140,24 @@ WX_DECLARE_EXPORTED_HASH_MAP( wxHashKeyValue,
                               void*,
                               wxHashTableHash,
                               wxHashTableEqual,
                               void*,
                               wxHashTableHash,
                               wxHashTableEqual,
-                              wxHashTableBaseBase );
+                              wxHashTableBaseBaseBase );
+
+// hack: we should really have HASH_MULTI(MAP|SET), but this requires
+// less work
+
+class WXDLLIMPEXP_BASE wxHashTableBaseBase : public wxHashTableBaseBaseBase
+{
+public:
+    wxHashTableBaseBase(size_t size, const wxHashTableHash& hash,
+                        const wxHashTableEqual& equal)
+        : wxHashTableBaseBaseBase(size, hash, equal)
+    { }
+
+    void multi_insert(const wxHashKeyValue& key, void* value)
+    {
+        CreateNodeLast(value_type(key, value));
+    }
+};
 
 class WXDLLIMPEXP_BASE wxHashTableBase
 {
 
 class WXDLLIMPEXP_BASE wxHashTableBase
 {
@@ -176,7 +193,7 @@ protected:
         wxASSERT( m_keyType == wxKEY_INTEGER );
 
         wxHashKeyValue k; k.integer = key;
         wxASSERT( m_keyType == wxKEY_INTEGER );
 
         wxHashKeyValue k; k.integer = key;
-        m_map[k] = data;
+        m_map.multi_insert(k, data);
     }
 
     void DoPut( const wxChar* key, void* data )
     }
 
     void DoPut( const wxChar* key, void* data )
@@ -184,17 +201,8 @@ protected:
         wxASSERT( m_keyType == wxKEY_STRING );
 
         wxHashKeyValue k;
         wxASSERT( m_keyType == wxKEY_STRING );
 
         wxHashKeyValue k;
-        k.string = (wxChar*)key;
-        wxHashTableBaseBase::iterator it = m_map.find(k);
-
-        if( it == m_map.end() )
-        {
-            k.string = new wxChar[wxStrlen(key) + 1];
-            wxStrcpy(k.string, key);
-            m_map[k] = data;
-        }
-        else
-            it->second = data;
+        k.string = wxStrcpy(new wxChar[wxStrlen(key) + 1], key);
+        m_map.multi_insert(k, data);
     }
 
     void* DoGet( long key ) const
     }
 
     void* DoGet( long key ) const
@@ -407,8 +415,8 @@ public:
     wxObject *Get(const wxChar *value) const { return (wxObject*)DoGet( value ); }
 
     // Deletes entry and returns data if found
     wxObject *Get(const wxChar *value) const { return (wxObject*)DoGet( value ); }
 
     // Deletes entry and returns data if found
-    wxObject *Delete(long key) { return (wxObject*)DoGet( key ); }
-    wxObject *Delete(const wxChar *key) { return (wxObject*)DoGet( key ); }
+    wxObject *Delete(long key) { return (wxObject*)DoDelete( key ); }
+    wxObject *Delete(const wxChar *key) { return (wxObject*)DoDelete( key ); }
 
 #if 0
     // Construct your own integer key from a string, e.g. in case
 
 #if 0
     // Construct your own integer key from a string, e.g. in case
index 5924d715761ae729aa59da7c51fbc1a1e21bd0c8..fbabe5b8f287997da19d41dcae45c357a8a82c42 100644 (file)
@@ -297,6 +297,19 @@ protected: \
  \
         return node; \
     } \
  \
         return node; \
     } \
+    void CreateNodeLast( const value_type& value )                           \
+    {                                                                        \
+        size_t bucket = m_hasher( m_getKey(value) ) % m_tableBuckets;        \
+        Node* curr = m_table[bucket],                                        \
+            * next = m_table[bucket];                                        \
+        while( next ) { curr = next; next = next->m_next(); }                \
+        Node** ptr = curr ? (Node**)&curr->m_nxt : &m_table[bucket];         \
+        *ptr = new Node( value );                                            \
+        /* must be after the node is inserted */                             \
+        ++m_items;                                                           \
+        if( SHOULD_GROW( m_tableBuckets, m_items ) )                         \
+            ResizeTable( m_tableBuckets );                                   \
+    }                                                                        \
     void CreateNode( const value_type& value ) \
     {\
         CreateNode(value, m_hasher( m_getKey(value) ) % m_tableBuckets ); \
     void CreateNode( const value_type& value ) \
     {\
         CreateNode(value, m_hasher( m_getKey(value) ) % m_tableBuckets ); \
index 7906063b3c83a74976a6c1105c78e511c146154f..42df7b135b69300b76688eec057310ea78f8f588 100644 (file)
@@ -1152,10 +1152,11 @@ static void TestHash()
 
     {
         wxHashTable hash(wxKEY_INTEGER), hash2(wxKEY_STRING);
 
     {
         wxHashTable hash(wxKEY_INTEGER), hash2(wxKEY_STRING);
+        wxObject o;
         int i;
 
         for ( i = 0; i < 100; ++i )
         int i;
 
         for ( i = 0; i < 100; ++i )
-            hash.Put(i, (wxObject*)&i + i);
+            hash.Put(i, &o + i);
 
         hash.BeginFind();
         wxHashTable::compatibility_iterator it = hash.Next();
 
         hash.BeginFind();
         wxHashTable::compatibility_iterator it = hash.Next();
@@ -1171,18 +1172,50 @@ static void TestHash()
             wxPuts(_T("Error in wxHashTable::compatibility_iterator\n"));
 
         for ( i = 99; i >= 0; --i )
             wxPuts(_T("Error in wxHashTable::compatibility_iterator\n"));
 
         for ( i = 99; i >= 0; --i )
-            if( hash.Get(i) != (wxObject*)&i + i )
+            if( hash.Get(i) != &o + i )
                 wxPuts(_T("Error in wxHashTable::Get/Put\n"));
 
                 wxPuts(_T("Error in wxHashTable::Get/Put\n"));
 
-        hash2.Put("foo", (wxObject*)&i + 1);
-        hash2.Put("bar", (wxObject*)&i + 2);
-        hash2.Put("baz", (wxObject*)&i + 3);
+        for ( i = 0; i < 100; ++i )
+            hash.Put(i, &o + i + 20);
+
+        for ( i = 99; i >= 0; --i )
+            if( hash.Get(i) != &o + i)
+                wxPuts(_T("Error (2) in wxHashTable::Get/Put\n"));
+
+        for ( i = 0; i < 50; ++i )
+            if( hash.Delete(i) != &o + i)
+                wxPuts(_T("Error in wxHashTable::Delete\n"));
+
+        for ( i = 50; i < 100; ++i )
+            if( hash.Get(i) != &o + i)
+                wxPuts(_T("Error (3) in wxHashTable::Get/Put\n"));
+
+        for ( i = 0; i < 50; ++i )
+            if( hash.Get(i) != &o + i + 20)
+                wxPuts(_T("Error (4) in wxHashTable::Put/Delete\n"));
 
 
-        if (hash2.Get("moo") != NULL)
+        for ( i = 0; i < 50; ++i )
+            if( hash.Delete(i) != &o + i + 20)
+                wxPuts(_T("Error (2) in wxHashTable::Delete\n"));
+
+        for ( i = 0; i < 50; ++i )
+            if( hash.Get(i) != NULL)
+                wxPuts(_T("Error (5) in wxHashTable::Put/Delete\n"));
+
+        hash2.Put(_T("foo"), &o + 1);
+        hash2.Put(_T("bar"), &o + 2);
+        hash2.Put(_T("baz"), &o + 3);
+
+        if (hash2.Get(_T("moo")) != NULL)
             wxPuts(_T("Error in wxHashTable::Get\n"));
 
             wxPuts(_T("Error in wxHashTable::Get\n"));
 
-        if (hash2.Get("bar") != (wxObject*)&i + 2)
+        if (hash2.Get(_T("bar")) != &o + 2)
             wxPuts(_T("Error in wxHashTable::Get/Put\n"));
             wxPuts(_T("Error in wxHashTable::Get/Put\n"));
+
+        hash2.Put(_T("bar"), &o + 0);
+
+        if (hash2.Get(_T("bar")) != &o + 2)
+            wxPuts(_T("Error (2) in wxHashTable::Get/Put\n"));
     }
 #if !wxUSE_STL
     {
     }
 #if !wxUSE_STL
     {