xref: /trunk/main/oox/inc/oox/helper/refmap.hxx (revision 7ee1d29c)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 #ifndef OOX_HELPER_REFMAP_HXX
25 #define OOX_HELPER_REFMAP_HXX
26 
27 #include <map>
28 #include <boost/bind.hpp>
29 #include <boost/shared_ptr.hpp>
30 #include <sal/types.h>
31 
32 namespace oox {
33 
34 // ============================================================================
35 
36 /** Template for a map of ref-counted objects with additional accessor functions.
37 
38     An instance of the class RefMap< Type > stores elements of the type
39     ::boost::shared_ptr< Type >. The new accessor functions has() and get()
40     work correctly for nonexisting keys, there is no need to check the passed
41     key before.
42  */
43 template< typename KeyType, typename ObjType, typename CompType = ::std::less< KeyType > >
44 class RefMap : public ::std::map< KeyType, ::boost::shared_ptr< ObjType >, CompType >
45 {
46 public:
47     typedef ::std::map< KeyType, ::boost::shared_ptr< ObjType >, CompType > container_type;
48     typedef typename container_type::key_type                               key_type;
49     typedef typename container_type::mapped_type                            mapped_type;
50     typedef typename container_type::value_type                             value_type;
51     typedef typename container_type::key_compare                            key_compare;
52 
53 public:
54     /** Returns true, if the object accossiated to the passed key exists.
55         Returns false, if the key exists but points to an empty reference. */
has(key_type nKey) const56     inline bool         has( key_type nKey ) const
57                         {
58                             const mapped_type* pxRef = getRef( nKey );
59                             return pxRef && pxRef->get();
60                         }
61 
62     /** Returns a reference to the object accossiated to the passed key, or an
63         empty reference on error. */
get(key_type nKey) const64     inline mapped_type  get( key_type nKey ) const
65                         {
66                             if( const mapped_type* pxRef = getRef( nKey ) ) return *pxRef;
67                             return mapped_type();
68                         }
69 
70     /** Calls the passed functor for every contained object, automatically
71         skips all elements that are empty references. */
72     template< typename FunctorType >
forEach(const FunctorType & rFunctor) const73     inline void         forEach( const FunctorType& rFunctor ) const
74                         {
75                             ::std::for_each( this->begin(), this->end(), ForEachFunctor< FunctorType >( rFunctor ) );
76                         }
77 
78     /** Calls the passed member function of ObjType on every contained object,
79         automatically skips all elements that are empty references. */
80     template< typename FuncType >
forEachMem(FuncType pFunc) const81     inline void         forEachMem( FuncType pFunc ) const
82                         {
83                             forEach( ::boost::bind( pFunc, _1 ) );
84                         }
85 
86     /** Calls the passed member function of ObjType on every contained object,
87         automatically skips all elements that are empty references. */
88     template< typename FuncType, typename ParamType >
forEachMem(FuncType pFunc,ParamType aParam) const89     inline void         forEachMem( FuncType pFunc, ParamType aParam ) const
90                         {
91                             forEach( ::boost::bind( pFunc, _1, aParam ) );
92                         }
93 
94     /** Calls the passed member function of ObjType on every contained object,
95         automatically skips all elements that are empty references. */
96     template< typename FuncType, typename ParamType1, typename ParamType2 >
forEachMem(FuncType pFunc,ParamType1 aParam1,ParamType2 aParam2) const97     inline void         forEachMem( FuncType pFunc, ParamType1 aParam1, ParamType2 aParam2 ) const
98                         {
99                             forEach( ::boost::bind( pFunc, _1, aParam1, aParam2 ) );
100                         }
101 
102     /** Calls the passed member function of ObjType on every contained object,
103         automatically skips all elements that are empty references. */
104     template< typename FuncType, typename ParamType1, typename ParamType2, typename ParamType3 >
forEachMem(FuncType pFunc,ParamType1 aParam1,ParamType2 aParam2,ParamType3 aParam3) const105     inline void         forEachMem( FuncType pFunc, ParamType1 aParam1, ParamType2 aParam2, ParamType3 aParam3 ) const
106                         {
107                             forEach( ::boost::bind( pFunc, _1, aParam1, aParam2, aParam3 ) );
108                         }
109     /** Calls the passed functor for every contained object. Passes the key as
110         first argument and the object reference as second argument to rFunctor. */
111     template< typename FunctorType >
forEachWithKey(const FunctorType & rFunctor) const112     inline void         forEachWithKey( const FunctorType& rFunctor ) const
113                         {
114                             ::std::for_each( this->begin(), this->end(), ForEachFunctorWithKey< FunctorType >( rFunctor ) );
115                         }
116 
117     /** Calls the passed member function of ObjType on every contained object.
118         Passes the object key as argument to the member function. */
119     template< typename FuncType >
forEachMemWithKey(FuncType pFunc) const120     inline void         forEachMemWithKey( FuncType pFunc ) const
121                         {
122                             forEachWithKey( ::boost::bind( pFunc, _2, _1 ) );
123                         }
124 
125     /** Calls the passed member function of ObjType on every contained object.
126         Passes the object key as first argument to the member function. */
127     template< typename FuncType, typename ParamType >
forEachMemWithKey(FuncType pFunc,ParamType aParam) const128     inline void         forEachMemWithKey( FuncType pFunc, ParamType aParam ) const
129                         {
130                             forEachWithKey( ::boost::bind( pFunc, _2, _1, aParam ) );
131                         }
132 
133     /** Calls the passed member function of ObjType on every contained object.
134         Passes the object key as first argument to the member function. */
135     template< typename FuncType, typename ParamType1, typename ParamType2 >
forEachMemWithKey(FuncType pFunc,ParamType1 aParam1,ParamType2 aParam2) const136     inline void         forEachMemWithKey( FuncType pFunc, ParamType1 aParam1, ParamType2 aParam2 ) const
137                         {
138                             forEachWithKey( ::boost::bind( pFunc, _2, _1, aParam1, aParam2 ) );
139                         }
140 
141     /** Calls the passed member function of ObjType on every contained object.
142         Passes the object key as first argument to the member function. */
143     template< typename FuncType, typename ParamType1, typename ParamType2, typename ParamType3 >
forEachMemWithKey(FuncType pFunc,ParamType1 aParam1,ParamType2 aParam2,ParamType3 aParam3) const144     inline void         forEachMemWithKey( FuncType pFunc, ParamType1 aParam1, ParamType2 aParam2, ParamType3 aParam3 ) const
145                         {
146                             forEachWithKey( ::boost::bind( pFunc, _2, _1, aParam1, aParam2, aParam3 ) );
147                         }
148 
149 private:
150     template< typename FunctorType >
151     struct ForEachFunctor
152     {
153         FunctorType         maFunctor;
ForEachFunctoroox::RefMap::ForEachFunctor154         inline explicit     ForEachFunctor( const FunctorType& rFunctor ) : maFunctor( rFunctor ) {}
operator ()oox::RefMap::ForEachFunctor155         inline void         operator()( const value_type& rValue ) { if( rValue.second.get() ) maFunctor( *rValue.second ); }
156     };
157 
158     template< typename FunctorType >
159     struct ForEachFunctorWithKey
160     {
161         FunctorType         maFunctor;
ForEachFunctorWithKeyoox::RefMap::ForEachFunctorWithKey162         inline explicit     ForEachFunctorWithKey( const FunctorType& rFunctor ) : maFunctor( rFunctor ) {}
operator ()oox::RefMap::ForEachFunctorWithKey163         inline void         operator()( const value_type& rValue ) { if( rValue.second.get() ) maFunctor( rValue.first, *rValue.second ); }
164     };
165 
getRef(key_type nKey) const166     inline const mapped_type* getRef( key_type nKey ) const
167                         {
168                             typename container_type::const_iterator aIt = this->find( nKey );
169                             return (aIt == this->end()) ? 0 : &aIt->second;
170                         }
171 };
172 
173 // ============================================================================
174 
175 } // namespace oox
176 
177 #endif
178