MOAB: Mesh Oriented datABase
(version 5.4.1)
|
00001 #ifndef BIT_TAG_HPP 00002 #define BIT_TAG_HPP 00003 00004 #include "TagInfo.hpp" 00005 #include "Internals.hpp" 00006 #include <algorithm> 00007 #include <vector> 00008 #include <cassert> 00009 00010 namespace moab 00011 { 00012 00013 class BitPage; 00014 00015 /**\brief data for a single bit tag */ 00016 class BitTag : public TagInfo 00017 { 00018 private: 00019 BitTag( const char* name, int size, const void* default_value ) 00020 : TagInfo( name, size, MB_TYPE_BIT, default_value, default_value ? 1 : 0 ), requestedBitsPerEntity( 0 ), 00021 storedBitsPerEntity( 0 ), pageShift( 0 ) 00022 { 00023 } 00024 00025 public: 00026 static BitTag* create_tag( const char* name, int size, const void* default_value = 0 ); 00027 00028 virtual ~BitTag(); 00029 00030 virtual TagType get_storage_type() const; 00031 00032 /**\brief Remove/clear tag data for all entities 00033 * 00034 * Remove tag values from entities. 00035 * 00036 *\param delete_pending If true, then release any global 00037 * data associated with the tag in preparation for deleting 00038 * the tag itself. 00039 * 00040 *\Note Invalidates tag if \c tag_delete_pending is true. The only 00041 * valid method that can be invoked that is is the destructor. 00042 * 00043 *\param seqman Pointer to mesh entity database 00044 */ 00045 virtual ErrorCode release_all_data( SequenceManager* seqman, Error* error_handler, bool delete_pending ); 00046 00047 /**\brief Get tag value for passed entities 00048 * 00049 * Get tag values for specified entities. 00050 * 00051 *\Note Will fail for variable-length data. 00052 *\param seqman Pointer to mesh entity database 00053 *\param entities Entity handles for which to retrieve tag data 00054 *\param num_entities Length of \c entities array 00055 *\param data Pointer to memory in which to store consecutive tag values, 00056 * one for each passed entity. 00057 */ 00058 virtual ErrorCode get_data( const SequenceManager* seqman, 00059 Error* error_handler, 00060 const EntityHandle* entities, 00061 size_t num_entities, 00062 void* data ) const; 00063 00064 /**\brief Get tag value for passed entities 00065 * 00066 * Get tag values for specified entities. 00067 * 00068 *\Note Will fail for variable-length data. 00069 *\param seqman Pointer to mesh entity database 00070 *\param entities Entity handles for which to retrieve tag data 00071 *\param data Pointer to memory in which to store consecutive tag values, 00072 * one for each passed entity. 00073 */ 00074 virtual ErrorCode get_data( const SequenceManager* seqman, 00075 Error* error_handler, 00076 const Range& entities, 00077 void* data ) const; 00078 00079 /**\brief Get tag value for passed entities 00080 * 00081 * Get tag values for specified entities. 00082 * 00083 *\param seqman Pointer to mesh entity database 00084 *\param entities Entity handles for which to retrieve tag data 00085 *\param num_entities Length of \c entities array 00086 *\param data_ptrs Array of pointers to tag values, one pointer 00087 * for each passed entity. 00088 *\param data_lengths One value for each entity specifying the 00089 * length of the tag value for the corresponding 00090 * entity. 00091 */ 00092 virtual ErrorCode get_data( const SequenceManager* seqman, 00093 Error* error_handler, 00094 const EntityHandle* entities, 00095 size_t num_entities, 00096 const void** data_ptrs, 00097 int* data_lengths ) const; 00098 00099 /**\brief Get tag value for passed entities 00100 * 00101 * Get tag values for specified entities. 00102 * 00103 *\param seqman Pointer to mesh entity database 00104 *\param entities Entity handles for which to retrieve tag data 00105 *\param data_ptrs Array of pointers to tag values, one pointer 00106 * for each passed entity. 00107 *\param data_lengths One value for each entity specifying the 00108 * length of the tag value for the corresponding 00109 * entity. 00110 */ 00111 virtual ErrorCode get_data( const SequenceManager* seqman, 00112 Error* error_handler, 00113 const Range& entities, 00114 const void** data_ptrs, 00115 int* data_lengths ) const; 00116 00117 /**\brief Set tag value for passed entities 00118 * 00119 * Store tag data or update stored tag values 00120 *\Note Will fail for variable-length data. 00121 *\param seqman Pointer to mesh entity database 00122 *\param entities Entity handles for which to store tag data 00123 *\param num_entities Length of \c entities array 00124 *\param data Pointer to memory holding consecutive tag values, 00125 * one for each passed entity. 00126 */ 00127 virtual ErrorCode set_data( SequenceManager* seqman, 00128 Error* error_handler, 00129 const EntityHandle* entities, 00130 size_t num_entities, 00131 const void* data ); 00132 00133 /**\brief Set tag value for passed entities 00134 * 00135 * Store tag data or update stored tag values 00136 *\Note Will fail for variable-length data. 00137 *\param seqman Pointer to mesh entity database 00138 *\param entities Entity handles for which to store tag data 00139 *\param data Pointer to memory holding consecutive tag values, 00140 * one for each passed entity. 00141 */ 00142 virtual ErrorCode set_data( SequenceManager* seqman, 00143 Error* error_handler, 00144 const Range& entities, 00145 const void* data ); 00146 00147 /**\brief Set tag value for passed entities 00148 * 00149 * Store tag data or update stored tag values 00150 * 00151 *\param seqman Pointer to mesh entity database 00152 *\param entities Entity handles for which to store tag data 00153 *\param num_entities Length of \c entities array 00154 *\param data_ptrs Array of pointers to tag values, one pointer 00155 * for each passed entity. 00156 *\param data_lengths One value for each entity specifying the 00157 * length of the tag value for the corresponding 00158 * entity. Array is required for variable-length 00159 * tags and is ignored for fixed-length tags. 00160 */ 00161 virtual ErrorCode set_data( SequenceManager* seqman, 00162 Error* error_handler, 00163 const EntityHandle* entities, 00164 size_t num_entities, 00165 void const* const* data_ptrs, 00166 const int* data_lengths ); 00167 00168 /**\brief Set tag value for passed entities 00169 * 00170 * Store tag data or update stored tag values 00171 * 00172 *\param seqman Pointer to mesh entity database 00173 *\param entities Entity handles for which to store tag data 00174 *\param data_ptrs Array of pointers to tag values, one pointer 00175 * for each passed entity. 00176 *\param data_lengths One value for each entity specifying the 00177 * length of the tag value for the corresponding 00178 * entity. Array is required for variable-length 00179 * tags and is ignored for fixed-length tags. 00180 */ 00181 virtual ErrorCode set_data( SequenceManager* seqman, 00182 Error* error_handler, 00183 const Range& entities, 00184 void const* const* data_ptrs, 00185 const int* data_lengths ); 00186 00187 /**\brief Set tag value for passed entities 00188 * 00189 * Store tag data or update stored tag values. 00190 * 00191 *\param seqman Pointer to mesh entity database 00192 *\param entities Entity handles for which to store tag data 00193 *\param num_entities Length of \c entities array 00194 *\param value_ptr Pointer to a single tag value which is to be 00195 * stored for each of the passed entities. 00196 *\param value_len Length of tag value in bytes. Ignored for 00197 * fixed-length tags. Required for variable- 00198 * length tags. 00199 */ 00200 virtual ErrorCode clear_data( SequenceManager* seqman, 00201 Error* error_handler, 00202 const EntityHandle* entities, 00203 size_t num_entities, 00204 const void* value_ptr, 00205 int value_len = 0 ); 00206 00207 /**\brief Set tag value for passed entities 00208 * 00209 * Store tag data or update stored tag values. 00210 * 00211 *\param seqman Pointer to mesh entity database 00212 *\param entities Entity handles for which to store tag data 00213 *\param value_ptr Pointer to a single tag value which is to be 00214 * stored for each of the passed entities. 00215 *\param value_len Length of tag value in bytes. Ignored for 00216 * fixed-length tags. Required for variable- 00217 * length tags. 00218 */ 00219 virtual ErrorCode clear_data( SequenceManager* seqman, 00220 Error* error_handler, 00221 const Range& entities, 00222 const void* value_ptr, 00223 int value_len = 0 ); 00224 00225 /**\brief Remove/clear tag data for entities 00226 * 00227 * Remove tag values from entities. 00228 * 00229 *\param seqman Pointer to mesh entity database 00230 *\param entities Entity handles for which to store tag data 00231 *\param num_entities Length of \c entities array 00232 */ 00233 virtual ErrorCode remove_data( SequenceManager* seqman, 00234 Error* error_handler, 00235 const EntityHandle* entities, 00236 size_t num_entities ); 00237 00238 /**\brief Remove/clear tag data for entities 00239 * 00240 * Remove tag values from entities. 00241 * 00242 *\param seqman Pointer to mesh entity database 00243 *\param entities Entity handles for which to store tag data 00244 */ 00245 virtual ErrorCode remove_data( SequenceManager* seqman, Error* error_handler, const Range& entities ); 00246 00247 /**\brief Access tag data via direct pointer into contiguous blocks 00248 * 00249 * Iteratively obtain direct access to contiguous blocks of tag 00250 * storage. This function cannot be used with bit tags because 00251 * of the compressed bit storage. This function cannot be used 00252 * with variable length tags because it does not provide a mechanism 00253 * to determine the length of the value for each entity. This 00254 * function may be used with sparse tags, but if it is used, it 00255 * will return data for a single entity at a time. 00256 * 00257 *\param iter As input, the first entity for which to return 00258 * data. As output, one past the last entity for 00259 * which data was returned. 00260 *\param end One past the last entity for which data is desired 00261 *\param data_ptr Output: pointer to tag storage. 00262 * 00263 *\Note If this function is called for entities for which no tag value 00264 * has been set, but for which a default value exists, it will 00265 * force the allocation of explicit storage for each such entity 00266 * even though MOAB would normally not explicitly store tag values 00267 * for such entities. 00268 */ 00269 virtual ErrorCode tag_iterate( SequenceManager* seqman, 00270 Error* error_handler, 00271 Range::iterator& iter, 00272 const Range::iterator& end, 00273 void*& data_ptr, 00274 bool allocate = true ); 00275 00276 /**\brief Get all tagged entities 00277 * 00278 * Get the list of entities for which the a tag value has been set, 00279 * or a close approximation if the tag storage scheme cannot 00280 * accurately determine exactly which entities have explicit values. 00281 * 00282 *\param seqman Pointer to entity storage database 00283 *\param output_entities Results *appended* to this range 00284 *\param type Optional entity type. If specified, search is 00285 * limited to entities of specified type. 00286 *\param intersect Optional intersect list. If specified, 00287 * search is restricted to entities in this list. 00288 */ 00289 virtual ErrorCode get_tagged_entities( const SequenceManager* seqman, 00290 Range& output_entities, 00291 EntityType type = MBMAXTYPE, 00292 const Range* intersect = 0 ) const; 00293 00294 /**\brief Count all tagged entities 00295 * 00296 * Count the entities for which the a tag value has been set, 00297 * or a close approximation if the tag storage scheme cannot 00298 * accurately determine exactly which entities have explicit values. 00299 * 00300 *\param seqman Pointer to entity storage database 00301 *\param output_count This is *incremented* for each detected entity. 00302 *\param type Optional entity type. If specified, search is 00303 * limited to entities of specified type. 00304 *\param intersect Optional intersect list. If specified, 00305 * search is restricted to entities in this list. 00306 */ 00307 virtual ErrorCode num_tagged_entities( const SequenceManager* seqman, 00308 size_t& output_count, 00309 EntityType type = MBMAXTYPE, 00310 const Range* intersect = 0 ) const; 00311 00312 /**\brief Get all tagged entities with tag value 00313 * 00314 * Get the list of entities which have the specified tag value. 00315 * 00316 *\param seqman Pointer to entity storage database 00317 *\param output_entities Results *appended* to this range 00318 *\param value Pointer to tag value 00319 *\param value_bytes Size of tag value in bytes. 00320 *\param type Optional entity type. If specified, search is 00321 * limited to entities of specified type. 00322 *\param intersect_entities Optional intersect list. If specified, 00323 * search is restricted to entities in this list. 00324 */ 00325 virtual ErrorCode find_entities_with_value( const SequenceManager* seqman, 00326 Error* error_handler, 00327 Range& output_entities, 00328 const void* value, 00329 int value_bytes = 0, 00330 EntityType type = MBMAXTYPE, 00331 const Range* intersect_entities = 0 ) const; 00332 00333 /**\brief Check if entity is tagged */ 00334 virtual bool is_tagged( const SequenceManager*, EntityHandle h ) const; 00335 00336 /**\brief Get memory use for tag data. 00337 * 00338 */ 00339 ErrorCode get_memory_use( const SequenceManager* seqman, unsigned long& total, unsigned long& per_entity ) const; 00340 00341 /**\brief Get entities for which an explicit tag of the specified value is stored */ 00342 ErrorCode get_entities_with_bits( EntityType type, Range& entities, unsigned char bits ) const; 00343 00344 /**\brief Get entities for which an explicit tag of the specified value is stored */ 00345 ErrorCode get_entities_with_bits( const Range& range, EntityType type, Range& entities, unsigned char bits ) const; 00346 00347 enum 00348 { 00349 Ln2PageSize = 12, //!< Constant: log2(PageSize) 00350 PageSize = ( 1u << Ln2PageSize ) //!< Constant: Bytes per BitPage (power of 2) 00351 }; 00352 00353 private: 00354 BitTag( const BitTag& ); 00355 BitTag& operator=( const BitTag& ); 00356 ErrorCode reserve( unsigned bits ); 00357 00358 inline unsigned char default_val() const 00359 { 00360 if( get_default_value() ) 00361 return *reinterpret_cast< const unsigned char* >( get_default_value() ); 00362 else 00363 return 0; 00364 } 00365 00366 std::vector< BitPage* > pageList[MBMAXTYPE]; //!< Array of BitPage instances storing actual data. 00367 unsigned int requestedBitsPerEntity; //!< user-requested bits per entity 00368 unsigned int storedBitsPerEntity; //!< allocated bits per entity (power of 2) 00369 unsigned int pageShift; //!< log2( ents_per_page() ) 00370 00371 /**\brief Get indices from handle 00372 * 00373 *\param type Output: entity type 00374 *\param page Output: index into pageList[type] 00375 *\param offset Output: index into pageList[type][page] 00376 */ 00377 void unpack( EntityHandle h, EntityType& type, size_t& page, int& offset ) const 00378 { 00379 type = TYPE_FROM_HANDLE( h ); 00380 h = ID_FROM_HANDLE( h ); 00381 page = ( (size_t)h ) >> pageShift; // h / ents_per_page() 00382 offset = h & ( ( 1u << pageShift ) - 1u ); // h % ends_per_page() 00383 } 00384 00385 /**\brief Get the number of tag values that are stored in each BitPage */ 00386 int ents_per_page() const 00387 { 00388 return 8 * PageSize / storedBitsPerEntity; 00389 } 00390 00391 template < class Container > 00392 inline void get_tagged( EntityType type, Container& entities ) const; 00393 template < class Container > 00394 inline void get_tagged( Range::const_iterator begin, Range::const_iterator end, Container& entities ) const; 00395 template < class Container > 00396 inline void get_tagged( Container& entities, EntityType type, const Range* intersect ) const; 00397 }; 00398 00399 } // namespace moab 00400 00401 #endif