[2.2.1] Merge different codes between 2.2 and 3.0
[platform/framework/native/appfw.git] / inc / FBaseColMultiHashMap.h
1 //
2 // Copyright (c) 2012 Samsung Electronics Co., Ltd.
3 //
4 // Licensed under the Apache License, Version 2.0 (the License);
5 // you may not use this file except in compliance with the License.
6 // You may obtain a copy of the License at
7 //
8 // http://www.apache.org/licenses/LICENSE-2.0
9 //
10 // Unless required by applicable law or agreed to in writing, software
11 // distributed under the License is distributed on an "AS IS" BASIS,
12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 // See the License for the specific language governing permissions and
14 // limitations under the License.
15 //
16
17 /**
18  * @file                FBaseColMultiHashMap.h
19  * @brief               This is the header file for the %MultiHashMap class.
20  *
21  * This header file contains the declarations of the %MultiHashMap class.
22  */
23 #ifndef _FBASE_COL_MULTI_HASH_MAP_H_
24 #define _FBASE_COL_MULTI_HASH_MAP_H_
25
26 #include <FBaseObject.h>
27 #include <FBaseColIComparer.h>
28 #include <FBaseColIHashCodeProvider.h>
29 #include <FBaseColIMultiMap.h>
30
31 namespace Tizen { namespace Base { namespace Collection
32 {
33
34 class _MultiHashMapEntry;
35
36 /**
37  * @class MultiHashMap
38  * @brief This class represents a collection of associated keys and values that are organized based on the hash code of the key.
39  *
40  * @since 2.0
41  *
42  *  The %MultiHashMap class represents a collection of associated keys and values that are organized based on the hash code of the key.
43  * There is no limit on the number of elements with the same key, but duplicated elements with the same key are not allowed.
44  * The key and value cannot be @c null.
45  * @n
46  * For more information on the class features, see <a href="../org.tizen.native.appprogramming/html/guide/base/hashmap_multihashmap.htm">HashMap and MultiHashMap</a>.
47  *
48  * The following example demonstrates how to use the %MultiHashMap class.
49  *
50  * @code
51  *      #include <FBase.h>
52  *
53  *      using namespace Tizen::Base;
54  *      using namespace Tizen::Base::Collection;
55  *
56  *      void
57  *      MyClass::MultiHashMapSample(void)
58  *      {
59  *              MultiHashMap map(SingleObjectDeleter);
60  *
61  *              // Constructs a MultiHashMap instance with default values for capacity, load factor, hash code provider, and comparer
62  *              map.Construct();
63  *
64  *              map.Add(new String(L"Zero"), new Integer(0));           // map.GetCount() : 1, map : (Zero -> 0)
65  *              map.Add(new String(L"One"), new Integer(1));            // map.GetCount() : 2, map : (Zero -> 0), (one -> 1)
66  *              map.Add(new String(L"Two"), new Integer(2));            // map.GetCount() : 3, map : (Zero -> 0), (one -> 1), (Two -> 2)
67  *              map.Add(new String(L"Two"), new Integer(20));           // map.GetCount() : 4, map : (Zero -> 0), (One -> 1), (Two -> 2, 20)
68  *
69  *              // Gets values with the specified key
70  *              Integer*        pValue = null;
71  *              IEnumerator *pValueEnum = map.GetValuesN(String(L"Two"));
72  *              while(pValueEnum->MoveNext() == E_SUCCESS)
73  *              {
74  *                      pValue = static_cast< Integer* > (pValueEnum->GetCurrent());
75  *              }
76  *
77  *              delete pValueEnum;
78  *
79  *              // Removes values with the specified key     // String(L"Two"), Integer(2), Integer(20) are removed
80  *              map.Remove(String(L"Two"));
81  *
82  *              // Uses an enumerator to access elements in the map
83  *              IMapEnumerator* pMapEnum = map.GetMapEnumeratorN();
84  *              String* pKey = null;
85  *              while (pMapEnum->MoveNext() == E_SUCCESS)
86  *              {
87  *                      pKey = static_cast< String* > (pMapEnum->GetKey());
88  *                      pValue = static_cast< Integer* > (pMapEnum->GetValue());
89  *              }
90  *
91  *              delete pMapEnum;
92  *
93  *              // Deallocates all objects
94  *              // Because the destructor calls RemoveAll() internally, you do not need to call RemoveAll() to destroy all elements at the end.
95  *              // map.RemoveAll();
96  *      }
97  * @endcode
98  */
99 class _OSP_EXPORT_ MultiHashMap
100         : public IMultiMap
101         , public Object
102 {
103 public:
104         using IMultiMap::Add;
105         using IMultiMap::Remove;
106         using IMultiMap::RemoveAll;
107         using IMultiMap::SetValue;
108         using IMultiMap::Contains;
109         using IMultiMap::ContainsKey;
110
111         /**
112          * The object is not fully constructed after this constructor is called. For full construction, @n
113          * the Construct() method must be called right after calling this constructor.
114          *
115          * @since 2.0
116          *
117          * @param[in]   deleter The function pointer to type of the element deleter
118          * @remarks     To create an owing collection, set the element deleter value as @c SingleObjectDeleter. This gives the collection the ownership of elements and the collection will destroy elements. @n
119          *                      On the other hand, to create a non-owning collection, you do not need to set the element deleter value, as @c NoOpDeleter is the default element deleter.
120          *                      It means that you do not transfer the ownership of elements to the collection.
121          * @see         NoOpDeleter()
122          * @see         SingleObjectDeleter()
123          * @see         ArrayDeleter()
124          */
125         explicit MultiHashMap(DeleterFunctionType deleter = NoOpDeleter);
126
127         /**
128          * This destructor overrides Tizen::Base::Object::~Object().
129          *
130          * @since 2.0
131          */
132         virtual ~MultiHashMap(void);
133
134         /**
135          * Initializes a new instance of %MultiHashMap with the specified capacity and load factor.
136          *
137          * @since 2.0
138          *
139          * @return              An error code
140          * @param[in]   capacity                The initial capacity
141          * @param[in]   loadFactor              The maximum ratio of elements to buckets
142          * @exception   E_SUCCESS               The method is successful.
143          * @exception   E_INVALID_ARG   A specified input parameter is invalid, or
144          *                                                              the @c capacity or the @c loadFactor is negative.
145          * @remarks             The GetHashCode() method of the key object is used for hashing and the
146          *                              Equals() method of the key object is used for comparing the keys.
147          * @see                 MultiHashMap()
148          */
149         result Construct(int capacity = 16, float loadFactor = 0.75);
150
151         /**
152          * Initializes a new instance of %MultiHashMap by copying the elements of the given map.
153          *
154          * @since 2.0
155          *
156          * @return              An error code
157          * @param[in]   map                             The map to copy
158          * @param[in]   loadFactor              The maximum ratio of elements to buckets @n
159          *                                                              If it is @c 0, the default load factor(0.75) is used.
160          * @exception   E_SUCCESS                       The method is successful.
161          * @exception   E_INVALID_ARG           The specified @c loadFactor is negative.
162          * @exception   E_INVALID_OPERATION     The current state of the instance prohibits the execution of the specified operation, or
163          *                                                                      the @c map is modified during the operation of this method.
164          * @remarks             This method performs a shallow copy. It copies just the pointer; not the element itself.
165          * @see                 MultiHashMap()
166          */
167         result Construct(const IMultiMap& map, float loadFactor = 0.75);
168
169
170         /**
171          * Initializes a new instance of the %MultiHashMap class, with the specified initial capacity, load factor, hash code provider, and comparer.
172          *
173          * @since 2.0
174          *
175          * @return              An error code
176          * @param[in]   capacity        The initial capacity @n
177          *                                                      If it is @c 0, the default capacity (16) is used.
178          * @param[in]   loadFactor      The maximum ratio of elements to buckets @n
179          *                                                      If it is @c 0, the default load factor (0.75) is used.
180          * @param[in]   provider        An instance of the IHashCodeProvider derived class that supplies the hash codes
181          *                                                      for all keys in this map
182          * @param[in]   comparer        An instance of the IComparer derived class to use when comparing keys
183          * @exception   E_SUCCESS               The method is successful.
184          * @exception   E_INVALID_ARG   A specified input parameter is invalid, or
185          *                                                              the @c capacity or the @c loadFactor is negative.
186          * @remarks             The instances of hash code provider and comparer will not be deallocated later from this map.
187          * @see                 MultiHashMap()
188          */
189         result Construct(int capacity, float loadFactor, const IHashCodeProvider& provider, const IComparer& comparer);
190
191         /**
192          * Initializes a new instance of the %MultiHashMap class by copying the elements of the specified map,
193          * with the specified load factor, hash code provider, and comparer.
194          *
195          * @since 2.0
196          *
197          * @return              An error code
198          * @param[in]   map                     A map to copy
199          * @param[in]   loadFactor      The maximum ratio of elements to buckets @n
200          *                                                      If it is @c 0, the default load factor (0.75) is used.
201          * @param[in]   provider        An instance of the IHashCodeProvider derived class that supplies the hash codes
202          *                                                      for all keys in this map
203          * @param[in]   comparer        An instance of the IComparer derived class to use when comparing keys
204          * @exception   E_SUCCESS                       The method is successful.
205          * @exception   E_INVALID_ARG           A specified input parameter is invalid, or
206          *                                                                      the @c loadFactor is negative.
207          * @exception   E_INVALID_OPERATION     The current state of the instance prohibits the execution of the specified operation, or
208          *                                                                      the @c map is modified during the operation of this method.
209          * @remarks             This method performs a shallow copy. It copies just the pointer; not the element itself.
210          *                      The instances of hash code provider and comparer will not be deallocated later from this map.
211          * @see                 MultiHashMap()
212          */
213         result Construct(const IMultiMap& map, float loadFactor, const IHashCodeProvider& provider, const IComparer& comparer);
214
215         /**
216          * Adds the specified key-value pair to this map.
217          *
218          * @since 2.0
219          *
220          * @return              An error code
221          * @param[in]   pKey    The pointer to key to add
222          * @param[in]   pValue  The pointer to corresponding value to add
223          * @exception   E_SUCCESS                       The method is successful.
224          * @exception   E_OBJ_ALREADY_EXIST     The specified pair of @c pKey and @c pValue already exists.
225          * @exception   E_INVALID_ARG           A specified input parameter is invalid, or
226          *                                                                      the comparer has failed to compare the keys.
227          * @remarks             This method performs a shallow copy. It adds just the pointer; not the element itself.
228          * @see                 Remove()
229          */
230         virtual result Add(Object* pKey, Object* pValue);
231
232         /**
233          * Gets an enumerator of this map.
234          *
235          * @since 2.0
236          *
237          * @return              An enumerator (an instance of the IEnumerator derived class) of this map, @n
238          *                              else @c null if some exception occurs
239          * @remarks             If the key has multiple values, the enumeration proceeds as follows: {A: a}, {B: b}, {B: c}, {B, d}, {C: e}, ...
240          *                              The specific error code can be accessed using the GetLastResult() method.
241          * @see                 IMapEnumerator
242          */
243         virtual IEnumerator* GetEnumeratorN(void) const;
244
245         /**
246          * Gets an enumerator of this map.
247          *
248          * @since 2.0
249          *
250          * @return              An enumerator (an instance of the IMapEnumerator derived class) of this map, @n
251          *                              else @c null if some exception occurs
252          * @remarks             If the key has multiple values, the enumeration proceeds as follows: {A: a}, {B: b}, {B: c}, {B, d}, {C: e}, ...
253          *                      The specific error code can be accessed using the GetLastResult() method.
254          * @see                 IEnumerator
255          */
256         virtual IMapEnumerator* GetMapEnumeratorN(void) const;
257
258         /**
259          * Gets an enumerator of the values associated with the specified key.
260          *
261          * @since 2.0
262          *
263          * @return              An enumerator (an instance of the IEnumerator derived class) of the values associated with the specified key, @n
264          *                              else @c null if some exception occurs
265          * @param[in]   key                             A key to locate
266          * @exception   E_SUCCESS                       The method is successful.
267          * @exception   E_INVALID_ARG           A specified input parameter is invalid, or
268          *                                                                      the comparer has failed to compare the keys.
269          * @exception   E_OBJ_NOT_FOUND         The specified @c key is not found in the map.
270          * @remarks             The specific error code can be accessed using the GetLastResult() method.
271          * @see                 SetValue()
272          */
273         virtual IEnumerator* GetValuesN(const Object& key) const;
274
275         /**
276          * Gets a list of all unique keys in this map.
277          *
278          * @since 2.0
279          *
280          * @return              A list of all unique keys in this map
281          * @remarks             The %IList stores just the pointers to the elements in the map, not the elements themselves.
282          *                              The specific error code can be accessed using the GetLastResult() method.
283          * @see                 GetValuesN()
284          */
285         virtual IList* GetKeysN(void) const;
286
287         /**
288          * Gets a list of all the values in this map.
289          *
290          * @since 2.0
291          *
292          * @return              A list of all the values in this map
293          * @remarks             The IList stores just the pointers to the elements in the map, not the elements themselves.
294          *                              The specific error code can be accessed using the GetLastResult() method.
295          * @see                 GetKeysN()
296          */
297         virtual IList* GetValuesN(void) const;
298
299         /**
300          * Removes all the values with the specified key.
301          *
302          * @since 2.0
303          *
304          * @return              An error code
305          * @param[in]   key                                     The key to remove
306          * @exception   E_SUCCESS                       The method is successful.
307          * @exception   E_INVALID_ARG           A specified input parameter is invalid, or
308          *                                                                      the comparer has failed to compare keys.
309          * @exception   E_OBJ_NOT_FOUND         The specified @c key is not found in the map.
310          * @see                 Add()
311          */
312         virtual result Remove(const Object& key);
313
314         /**
315          * Removes the specified value associated with the specified key.
316          *
317          * @since 2.0
318          *
319          * @return              An error code
320          * @param[in]   key             The key whose mapping is to remove from the map
321          * @param[in]   value   The value to remove
322          * @exception   E_SUCCESS                       The method is successful.
323          * @exception   E_INVALID_ARG           A specified input parameter is invalid, or
324          *                                                                      the comparer has failed to compare the keys.
325          * @exception   E_OBJ_NOT_FOUND         The specified @c key and @c value pair is not found in the map.
326          * @remarks             The specified key is also removed if there are no more values associated with it.
327          * @see                 Add()
328          */
329         virtual result Remove(const Object& key, const Object& value);
330
331         /**
332          * Removes all the object pointers in the @c collection. @n
333          *
334          * @since 2.0
335          *
336          * @remarks             This method can be called before deleting @c collection.
337          */
338         virtual void RemoveAll(void);
339
340         /**
341          * Sets the value associated with the given key with a new value.
342          *
343          * @since 2.0
344          *
345          * @return              An error code
346          * @param[in]   key                     The key for which the associated value needs to replace
347          * @param[in]   value           The value to replace
348          * @param[in]   pNewValue       The pointer to new value to replace the existing value
349          * @exception   E_SUCCESS                       The method is successful.
350          * @exception   E_INVALID_ARG           A specified input parameter is invalid, or
351          *                                                                      the comparer has failed to compare the keys.
352          * @exception   E_OBJ_NOT_FOUND         The specified @c key and @c value pair is not found in the map.
353          * @remarks             To add a new key-value pair, use the Add() method.
354          * @see                 Add()
355          * @see                 GetValuesN()
356          */
357         virtual result SetValue(const Object& key, const Object& value, Object* pNewValue);
358
359         /**
360          * Gets the number of values currently stored in this map.
361          *
362          * @since 2.0
363          *
364          * @return              The number of values currently stored in this map
365          */
366         virtual int GetCount(void) const;
367
368         /**
369          * Gets the number of values whose key matches the key.
370          *
371          * @since 2.0
372          *
373          * @return              An error code
374          * @param[in]   key     A key to locate
375          * @param[out]  count   The number of values whose key is the @c key
376          * @exception   E_SUCCESS                       The method is successful.
377          * @exception   E_INVALID_ARG           A specified input parameter is invalid, or
378          *                                                                      the comparer has failed to compare the keys.
379          * @exception   E_OBJ_NOT_FOUND         The specified @c key is not found in the map.
380          */
381         virtual result GetCount(const Object& key, int& count) const;
382
383         /**
384          * Checks whether the map contains the specified key and value.
385          *
386          * @since 2.0
387          *
388          * @return              @c true if the map contains the specified key and value pair, @n
389          *                              else @c false
390          * @param[in]   key             The key to locate
391          * @param[in]   value   The value to locate
392          * @exception   E_SUCCESS               The method is successful.
393          * @exception   E_INVALID_ARG   A specified input parameter is invalid, or
394          *                                                              the comparer has failed to compare the keys.
395          * @remarks             The specific error code can be accessed using the GetLastResult() method.
396          * @see                 ContainsKey()
397          * @see                 ContainsValue()
398          */
399         virtual bool Contains(const Object& key, const Object& value) const;
400
401         /**
402          * Checks whether the map contains the specified key.
403          *
404          * @since 2.0
405          *
406          * @return              @c true if the map contains the specified key, @n
407          *                              else @c false
408          * @param[in]   key                     The key to locate
409          * @exception   E_SUCCESS               The method is successful.
410          * @exception   E_INVALID_ARG   A specified input parameter is invalid, or
411          *                                                              the comparer has failed to compare the keys.
412          * @remarks             The specific error code can be accessed using the GetLastResult() method.
413          * @see                 ContainsValue()
414          * @see                 Contains()
415          */
416         virtual bool ContainsKey(const Object& key) const;
417
418         /**
419          * Checks whether the map contains the specified value.
420          *
421          * @since 2.0
422          *
423          * @return              @c true if the map contains the specified value, @n
424          *                              else @c false
425          * @param[in]   value   The value to locate
426          *
427          * @see                         ContainsKey()
428          * @see                         Contains()
429          */
430         virtual bool ContainsValue(const Object& value) const;
431
432         /**
433          * Compares the specified instance to the current instance for equality.
434          *
435          * @since 2.0
436          *
437          * @return              @c true if the two instances are equal, @n
438          *                              @c false
439          * @param[in]   obj The object to compare with the current instance
440          * @remarks             This method returns @c true only if the specified object is also an instance of %MultiHashMap class,
441          *                              both maps have the same number of elements, and both maps contain the same elements.
442          */
443         virtual bool Equals(const Object& obj) const;
444
445         /**
446          * Gets the hash value of the current instance.
447          *
448          * @since 2.0
449          *
450          * @return      The hash value of the current instance
451          * @remarks     The two Tizen::Base::Object::Equals() instances must return the same hash value. For better performance, @n
452          *                      the used hash function must generate a random distribution for all inputs.
453          */
454         virtual int GetHashCode(void) const;
455
456         /**
457          * Gets the element deleter of the collection.
458          *
459          * @since 2.0
460          *
461          * @return              A function pointer to the existing element deleter
462          */
463         virtual DeleterFunctionType GetDeleter(void) const;
464
465 private:
466         /**
467          * The implementation of this copy constructor is intentionally blank and declared as private to prohibit copying of objects.
468          *
469          * @param[in]   map An instance of %MultiHashMap to initialize the current instance
470          */
471         MultiHashMap(const MultiHashMap& map);
472
473         /**
474          * The implementation of this copy assignment operator is intentionally blank and declared as private to prohibit copying of objects.
475          *
476          * @param[in]   map An instance of %MultiHashMap
477          */
478         MultiHashMap& operator =(const MultiHashMap& map);
479
480         /**
481          * Copies all the pairs from the specified map to this map.
482          *
483          * @return              An error code
484          * @param[in]   map                                     The map to copy
485          * @exception   E_SUCCESS                       The method is successful.
486          * @exception   E_INVALID_OPERATION     The current state of the instance prohibits the execution of the specified operation. @n
487          *                                                                      The @c map is modified during the operation of this method.
488          */
489         result AddAll(const IMultiMap& map);
490
491         /**
492          * Gets a hash value for the specified object.
493          *
494          * @return              An @c int hash value for the specified object
495          * @param[in]   obj     The object to get hash value
496          */
497         int Hash(const Object& obj) const;
498
499         /**
500          * Rehashes the contents of this map into a new array with a
501          * larger capacity. @n
502          * This method is called automatically when the number of keys in this map reaches its threshold.
503          *
504          * @return              An error code
505          * @param[in]   newCapacity             The new capacity @n
506          *                                                              It must be a power of two and be greater than current capacity.
507          * @exception   E_SUCCESS               The method is successful.
508          */
509         result Resize(int newCapacity);
510
511         /**
512          * Clears all key-value pairs in this map.
513          */
514         void Reset(void);
515
516         /**
517          * Sets the element deleter of the collection.
518          *
519          * @since 2.0
520          *
521          * @param[in]   deleter A function pointer to the element deleter to set
522          */
523         virtual void SetDeleter(DeleterFunctionType deleter);
524
525         _MultiHashMapEntry** __pTable;
526         int __count;
527         int __capacity;
528         float __loadFactor;
529         int __threshold;
530         IHashCodeProvider* __pProvider;
531         IComparer* __pComparer;
532         bool __needToRemoveProviderComparer;
533         int __modCount;
534         DeleterFunctionType __deleter;
535         static const int DEFAULT_CAPACITY = 16;
536         static const float DEFAULT_LOAD_FACTOR;
537
538         friend class _MultiHashMapEnumerator;
539         friend class _MultiHashMapImpl;
540         class _MultiHashMapImpl* __pMultiHashMapImpl;
541
542 }; // MultiHashMap
543
544 }}} // Tizen::Base::Collection
545
546 #endif //_FBASE_COL_MULTI_HASH_MAP_H_