karrayul.h

Go to the documentation of this file.
00001 
00004 #ifndef FBXFILESDK_COMPONENTS_KBASELIB_KLIB_KARRAYUL_H
00005 #define FBXFILESDK_COMPONENTS_KBASELIB_KLIB_KARRAYUL_H
00006 
00007 /**************************************************************************************
00008 
00009  Copyright (C) 2001 - 2009 Autodesk, Inc. and/or its licensors.
00010  All Rights Reserved.
00011 
00012  The coded instructions, statements, computer programs, and/or related material 
00013  (collectively the "Data") in these files contain unpublished information 
00014  proprietary to Autodesk, Inc. and/or its licensors, which is protected by 
00015  Canada and United States of America federal copyright law and by international 
00016  treaties. 
00017  
00018  The Data may not be disclosed or distributed to third parties, in whole or in
00019  part, without the prior written consent of Autodesk, Inc. ("Autodesk").
00020 
00021  THE DATA IS PROVIDED "AS IS" AND WITHOUT WARRANTY.
00022  ALL WARRANTIES ARE EXPRESSLY EXCLUDED AND DISCLAIMED. AUTODESK MAKES NO
00023  WARRANTY OF ANY KIND WITH RESPECT TO THE DATA, EXPRESS, IMPLIED OR ARISING
00024  BY CUSTOM OR TRADE USAGE, AND DISCLAIMS ANY IMPLIED WARRANTIES OF TITLE, 
00025  NON-INFRINGEMENT, MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE OR USE. 
00026  WITHOUT LIMITING THE FOREGOING, AUTODESK DOES NOT WARRANT THAT THE OPERATION
00027  OF THE DATA WILL BE UNINTERRUPTED OR ERROR FREE. 
00028  
00029  IN NO EVENT SHALL AUTODESK, ITS AFFILIATES, PARENT COMPANIES, LICENSORS
00030  OR SUPPLIERS ("AUTODESK GROUP") BE LIABLE FOR ANY LOSSES, DAMAGES OR EXPENSES
00031  OF ANY KIND (INCLUDING WITHOUT LIMITATION PUNITIVE OR MULTIPLE DAMAGES OR OTHER
00032  SPECIAL, DIRECT, INDIRECT, EXEMPLARY, INCIDENTAL, LOSS OF PROFITS, REVENUE
00033  OR DATA, COST OF COVER OR CONSEQUENTIAL LOSSES OR DAMAGES OF ANY KIND),
00034  HOWEVER CAUSED, AND REGARDLESS OF THE THEORY OF LIABILITY, WHETHER DERIVED
00035  FROM CONTRACT, TORT (INCLUDING, BUT NOT LIMITED TO, NEGLIGENCE), OR OTHERWISE,
00036  ARISING OUT OF OR RELATING TO THE DATA OR ITS USE OR ANY OTHER PERFORMANCE,
00037  WHETHER OR NOT AUTODESK HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH LOSS
00038  OR DAMAGE. 
00039 
00040 **************************************************************************************/
00041 #include <fbxfilesdk/components/kbaselib/kbaselib_h.h>
00042 
00043 #ifndef KFBX_PLUGIN
00044     #include <fbxfilesdk/components/kbaselib/klib/kdebug.h>
00045 #endif
00046 
00047 #include <string.h>
00048 #include <stdlib.h>
00049 
00050 #define KFBX_ARRAYUL_BLOCKSIZE 4
00051 
00052 #include <fbxfilesdk/components/kbaselib/kbaselib_forward.h>
00053 #include <fbxfilesdk/fbxfilesdk_nsbegin.h> // namespace
00054 
00055     /***********************************************************************
00056         CLASS KStaticArray
00057     ************************************************************************/
00058     template< class Type > class KBaseStaticArray
00059     {
00060         protected:
00061         int  mCount;
00062         Type *mArrayBuf;
00063 
00064         public:
00065         inline int GetCount() { return mCount; }
00066 
00068         inline Type &operator[](int pIndex)
00069         {
00070         #ifndef KFBX_PLUGIN
00071             K_ASSERT_MSG( pIndex >= 0   , "Buffer underflow");
00072             K_ASSERT_MSG( pIndex < mCount,"Buffer overflow.");
00073         #endif
00074             return mArrayBuf[pIndex];
00075         }
00076     };
00077 
00078     // Static Array
00079     template< class Type, int Count > class KStaticArray : public KBaseStaticArray<Type>
00080     {
00081         public:
00082         Type mArray[Count];
00083             inline KStaticArray(){ this->mArrayBuf = mArray; this->mCount = Count;}
00084     };
00085 
00086     template< class Type, int Count1, int Count2 > class KStaticArray2d
00087     {
00088         public:
00089 #if defined(KARCH_DEV_MSC) && (_MSC_VER <= 1200)// VC6
00090         KStaticArray<Type,Count2> *mArray;
00091 
00092         KStaticArray2d() { mArray = new KStaticArray<Type,Count2>(Count1); }
00093         ~KStaticArray2d() { delete[] mArray; }
00094 #else
00095         KStaticArray<Type,Count2> mArray[Count1];
00096 #endif
00097 
00098         // Access pointer at given index.
00099         inline KStaticArray< Type, Count2 > &operator[](int pIndex)
00100         {
00101         #ifndef KFBX_PLUGIN
00102             K_ASSERT_MSG( pIndex >= 0   , "Buffer underflow.");
00103             K_ASSERT_MSG( pIndex < Count1,"Buffer overflow.");
00104         #endif
00105             return mArray[pIndex];
00106         }
00107     };
00108 
00109     /***********************************************************************
00110         CLASS KArrayTemplate
00111     ************************************************************************/
00112     class  KBaseArraySize {
00113         public:
00114             KBaseArraySize( int pItemSize)
00115                 : mItemSize(pItemSize)
00116             {
00117             }
00118             inline int GetTypeSize() const { return mItemSize; }
00119         private:
00120             int mItemSize;
00121     };
00122 
00123     template <class T> class  KBaseArraySizeType
00124     {
00125         public:
00126             inline int GetTypeSize() const { return sizeof(T); }
00127     };
00128 
00129     // Helpers
00130     KFBX_DLL void KBaseArrayFree(char*);
00131     KFBX_DLL char* KBaseArrayRealloc(char*, size_t);
00132     
00134     //
00135     //  WARNING!
00136     //
00137     //  Anything beyond these lines may not be documented accurately and is
00138     //  subject to change without notice.
00139     //
00141     #ifndef DOXYGEN_SHOULD_SKIP_THIS
00142         KFBX_DLL void* KBaseArrayGetAlloc();
00143     #endif
00144 
00145     template <class TypeSize> class  KBaseArray
00146     {
00147         protected:
00148             struct KHeader {
00149                 int mArrayCount;
00150                 int mBlockCount;
00151             };
00152 
00153 
00154         protected:
00159             inline KBaseArray(TypeSize pTypeSize)
00160                 : mTypeSize(pTypeSize)
00161             {
00162                 mBaseArray  = NULL;
00163                 #ifndef KFBX_PLUGIN
00164                     K_ASSERT( pItemPerBlock > 0 );
00165                 #endif
00166             }
00167 
00168 
00170             inline ~KBaseArray(){
00171                 Clear ();
00172             }
00173 
00181             inline int      InsertAt(int pIndex, void *pItem)
00182             {
00183               int lArrayCount = GetArrayCount();
00184               int lBlockCount = GetBlockCount();
00185 
00186                 #ifndef KFBX_PLUGIN
00187                     K_ASSERT( pIndex >= 0 );
00188                 #endif
00189 
00190                 if (pIndex>lArrayCount) {
00191                     pIndex = GetArrayCount();
00192                 }
00193 
00194                 if (lArrayCount>= lBlockCount*KFBX_ARRAYUL_BLOCKSIZE)
00195                 {
00196                     // must Alloc.Realloc some new space
00197 
00198                     // double the number of blocks.
00199                     lBlockCount = ( 0 == lBlockCount ) ? 1 : lBlockCount * 2;
00200                     mBaseArray = KBaseArrayRealloc(mBaseArray, (size_t) (lBlockCount*KFBX_ARRAYUL_BLOCKSIZE*GetTypeSize()) + GetHeaderOffset() );
00201                     if(mBaseArray  == NULL)
00202                     {
00203                         return -1;
00204                     }
00205                 }
00206 
00207                 if (pIndex<lArrayCount)
00208                 {
00209                     // This is an insert
00210                     memmove (&(mBaseArray[(pIndex+1)*GetTypeSize()+ GetHeaderOffset() ]), &(mBaseArray[(pIndex)*GetTypeSize()+ GetHeaderOffset()] ), GetTypeSize()*(lArrayCount-pIndex));
00211                 }
00212 
00213                 memmove (&(mBaseArray[(pIndex)*GetTypeSize()+ GetHeaderOffset() ]), pItem, GetTypeSize());
00214 
00215                 SetArrayCount(lArrayCount+1);
00216                 SetBlockCount(lBlockCount);
00217 
00218                 return pIndex;
00219             }
00220 
00221 
00228             inline void*    GetAt(int pIndex)                           { return &(mBaseArray[(pIndex)*GetTypeSize()+ GetHeaderOffset() ]); }
00229 
00236             inline void RemoveAt(int pIndex)
00237             {
00238 
00239             #if defined(_DEBUG) && !defined(KARCH_ENV_MACOSX)
00240                 if (!ValidateIndex( pIndex ))
00241                 {
00242                     return;
00243                 }
00244             #endif
00245                 int lArrayCount = GetArrayCount();
00246                 if (pIndex+1<lArrayCount)
00247                 {
00248                     memmove (&(mBaseArray[(pIndex)*GetTypeSize()+ GetHeaderOffset() ]), &(mBaseArray[(pIndex+1)*GetTypeSize()+ GetHeaderOffset() ]), GetTypeSize()*(lArrayCount-pIndex-1));
00249                 }
00250 
00251                 SetArrayCount( lArrayCount-1 );
00252 
00253             #ifdef _DEBUG
00254                 memset( &(mBaseArray[(GetArrayCount())*GetTypeSize()+ GetHeaderOffset() ]),0,GetTypeSize());
00255             #endif
00256             }
00257 
00258 
00264             inline bool ValidateIndex( int pIndex ) const
00265             {
00266                 int lArrayCount = GetArrayCount();
00267                 if (pIndex>=0 && pIndex<lArrayCount)
00268                 {
00269                     return true;
00270                 } else
00271                 {
00272                     #ifndef KFBX_PLUGIN
00273                         K_ASSERT_MSG_NOW(_T("ArrayTemplate : Index out of range"));
00274                     #endif
00275                     return false;
00276                 }
00277             }
00278 
00279 
00280         public:
00284             inline int GetCount() const { return GetArrayCount(); }
00285 
00287             inline void Clear()
00288             {
00289                 if (mBaseArray!=NULL)
00290                 {
00291                     KBaseArrayFree(mBaseArray);
00292                     mBaseArray = NULL;
00293                 }
00294             }
00295 
00296 
00298             inline void Empty()
00299             {
00300             #ifndef KFBX_PLUGIN
00301                 #ifdef _DEBUG
00302                     memset( mBaseArray+ GetHeaderOffset() ,0,GetArrayCount()*GetTypeSize());
00303                 #endif
00304             #endif
00305                 SetArrayCount(0);
00306             }
00307 
00308 
00314             inline int      Reserve(int pCapacity)
00315             {
00316 
00317                 #ifndef KFBX_PLUGIN
00318                     K_ASSERT( pCapacity > 0 );
00319                 #endif
00320 
00321                 if( pCapacity )
00322                 {
00323                     const kUInt lTempNewBlockCount = ( (kUInt) (pCapacity + KFBX_ARRAYUL_BLOCKSIZE - 1 ) / KFBX_ARRAYUL_BLOCKSIZE );
00324                     const kUInt lNewBlockCount = (lTempNewBlockCount > 1 ? lTempNewBlockCount : 1);
00325 
00326                     int         lArrayCount   = GetArrayCount();
00327                     int         lBlockCount   = GetBlockCount();
00328 
00329                     const kUInt lOldArraySize = lArrayCount*GetTypeSize();
00330                     const kUInt lNewArraySize = lNewBlockCount*KFBX_ARRAYUL_BLOCKSIZE*GetTypeSize();
00331 
00332                     if (lNewBlockCount != (kUInt) lBlockCount)
00333                         mBaseArray = KBaseArrayRealloc(mBaseArray, (size_t) lNewArraySize+ GetHeaderOffset()  );
00334 
00335                     if( lNewBlockCount > (kUInt) lBlockCount ) {
00336                         memset( ((char*)mBaseArray+ GetHeaderOffset() ) + lOldArraySize, 0, (size_t) (lNewArraySize-lOldArraySize) );
00337                         SetArrayCount(lArrayCount);
00338                     } else if (pCapacity < lArrayCount)
00339                     {
00340                         memset( ((char*)mBaseArray+ GetHeaderOffset() ) + pCapacity*GetTypeSize(), 0, (size_t) (lNewArraySize-pCapacity*GetTypeSize()) );
00341                         SetArrayCount(pCapacity);
00342                     }
00343 
00344                     SetBlockCount(lNewBlockCount);
00345                 }
00346 
00347                 return GetBlockCount()*KFBX_ARRAYUL_BLOCKSIZE;
00348             }
00349 
00350 
00352             //  Differ from SetCount because array capacity can be lowered.
00353 
00359             inline void     SetCount (int pCount)
00360             {
00361             #ifndef KFBX_PLUGIN
00362             #ifdef _DEBUG
00363                 if (pCount<0)
00364                 {
00365                     K_ASSERT_MSG_NOW (_T("ArrayUL : Item count can't be negative"));
00366                     return ;
00367                 }
00368             #endif
00369             #endif
00370                 int lArrayCount = GetArrayCount();
00371                 if (pCount > lArrayCount)
00372                 {
00373                     AddMultiple( pCount-lArrayCount);
00374                 } else
00375                 {
00376                     SetArrayCount(pCount);
00377                 }
00378             }
00379 
00380             inline void     Resize(int pItemCount)
00381             {
00382                 #ifndef KFBX_PLUGIN
00383                     K_ASSERT( pItemCount >= 0 );
00384                 #endif
00385 
00386                 const kUInt lTempNewBlockCount = ( (kUInt) (pItemCount + KFBX_ARRAYUL_BLOCKSIZE - 1 ) / KFBX_ARRAYUL_BLOCKSIZE );
00387                 const kUInt lNewBlockCount = (lTempNewBlockCount > 1 ? lTempNewBlockCount : 1);
00388 
00389                 int         lArrayCount     = GetArrayCount();
00390                 int         lBlockCount   = GetBlockCount();
00391 
00392                 const kUInt lOldArraySize   = lArrayCount*GetTypeSize();
00393                 const kUInt lNewArraySize   = lNewBlockCount*KFBX_ARRAYUL_BLOCKSIZE*GetTypeSize();
00394 
00395                 if (lNewBlockCount != (kUInt) lBlockCount)
00396                     mBaseArray = KBaseArrayRealloc(mBaseArray, (size_t) lNewArraySize+ GetHeaderOffset()  );
00397 
00398                 if( lNewBlockCount > (kUInt) lBlockCount )
00399                     memset( ((char*)mBaseArray+ GetHeaderOffset() ) + lOldArraySize, 0, (size_t) (lNewArraySize-lOldArraySize) );
00400                 else if (pItemCount < lArrayCount)
00401                     memset( ((char*)mBaseArray+ GetHeaderOffset() ) + pItemCount*GetTypeSize(), 0, (size_t) (lNewArraySize-pItemCount*GetTypeSize()) );
00402 
00403                 SetBlockCount(lNewBlockCount);
00404                 SetArrayCount(pItemCount);
00405             }
00406 
00407             inline void     AddMultiple(int pItemCount)
00408             {
00409                 #ifndef KFBX_PLUGIN
00410                     K_ASSERT( pItemCount > 0 );
00411                 #endif
00412 
00413                 if( pItemCount )
00414                 {
00415                     int         lArrayCount = GetArrayCount();
00416                     int         lBlockCount = GetBlockCount();
00417                     const kUInt lTempNewBlockCount = ( (kUInt) (lArrayCount+pItemCount + KFBX_ARRAYUL_BLOCKSIZE - 1 ) / KFBX_ARRAYUL_BLOCKSIZE );
00418                     const kUInt lNewBlockCount = (lTempNewBlockCount > 1 ? lTempNewBlockCount : 1);
00419 
00420                     const kUInt lOldArraySize = lArrayCount*GetTypeSize();
00421                     const kUInt lNewArraySize = lNewBlockCount*KFBX_ARRAYUL_BLOCKSIZE*GetTypeSize();
00422 
00423                     #ifndef KFBX_PLUGIN
00424                         K_ASSERT( lOldArraySize < lNewArraySize );
00425                     #endif
00426 
00427                     if( lNewBlockCount > (kUInt) lBlockCount )
00428                     {
00429                         mBaseArray = KBaseArrayRealloc(mBaseArray, (size_t) lNewArraySize+ GetHeaderOffset()  );
00430                         lBlockCount = lNewBlockCount;
00431                     }
00432 
00433                     memset( ((char*)mBaseArray+ GetHeaderOffset() ) + lOldArraySize, 0, (size_t) (lNewArraySize-lOldArraySize) );
00434                     SetArrayCount ( lArrayCount + pItemCount );
00435                     SetBlockCount (lBlockCount);
00436                 }
00437             }
00438 
00439 
00440             inline int  GetTypeSize() const { return mTypeSize.GetTypeSize(); }
00441 
00443         //
00444         //  WARNING!
00445         //
00446         //  Anything beyond these lines may not be documented accurately and is
00447         //  subject to change without notice.
00448         //
00450         #ifndef DOXYGEN_SHOULD_SKIP_THIS
00451 
00452         protected:
00453             inline KHeader* const   GetHeader() const
00454             {
00455                 return (KHeader*    const   )mBaseArray;
00456             }
00457             inline KHeader*     GetHeader()
00458             {
00459                 return (KHeader*)mBaseArray;
00460             }
00461             inline int GetHeaderOffset() const
00462             {
00463                 return sizeof(KHeader);
00464             }
00465             inline int GetArrayCount() const
00466             {
00467                 return GetHeader() ? GetHeader()->mArrayCount : 0;
00468             }
00469             inline void SetArrayCount(int pArrayCount)
00470             {
00471                 if (GetHeader()) GetHeader()->mArrayCount=pArrayCount;
00472             }
00473             inline int GetBlockCount() const
00474             {
00475                 return GetHeader() ? GetHeader()->mBlockCount : 0;
00476             }
00477             inline void SetBlockCount(int pArrayCount)
00478             {
00479                 if (GetHeader()) GetHeader()->mBlockCount=pArrayCount;
00480             }
00481 
00482         protected:
00483             char*           mBaseArray;
00484             TypeSize        mTypeSize;
00485 
00486         #endif // #ifndef DOXYGEN_SHOULD_SKIP_THIS
00487 
00488     };
00489 
00490 
00492     #define VC6
00493 
00494     template < class Type > class  KArrayTemplate : public KBaseArray< KBaseArraySizeType<Type> >
00495     {
00496         typedef KBaseArray< KBaseArraySizeType<Type> > ParentClass;
00497 
00498 
00499     public:
00503         inline KArrayTemplate()
00504             : ParentClass (KBaseArraySizeType<Type>())
00505         {
00506         }
00507 
00509         inline KArrayTemplate(const KArrayTemplate& pArrayTemplate)
00510             : ParentClass (KBaseArraySizeType<Type>())
00511         {
00512             *this = pArrayTemplate;
00513         }
00514 
00515         inline ~KArrayTemplate() {}
00516 
00523         inline int InsertAt(int pIndex, Type pItem)
00524         {
00525             return ParentClass::InsertAt( pIndex,&pItem );
00526         }
00527 
00532         inline Type RemoveAt(int pIndex)
00533         {
00534             Type tmpItem = GetAt(pIndex);
00535             ParentClass::RemoveAt( pIndex );
00536             return tmpItem;
00537         }
00538 
00542         inline Type RemoveLast()
00543         {
00544             return RemoveAt(ParentClass::GetArrayCount()-1);
00545         }
00546 
00551         inline bool RemoveIt(Type pItem)
00552         {
00553             int Index = Find (pItem);
00554             if (Index>=0)
00555             {
00556                 RemoveAt (Index);
00557                 return true;
00558             }
00559             return false;
00560         }
00561 
00563         inline Type &operator[](int pIndex) const
00564         {
00565         #if defined(_DEBUG) && !defined(KARCH_ENV_MACOSX)
00566             if (!ParentClass::ValidateIndex( pIndex ))
00567             {
00568                 return (Type &)(ParentClass::mBaseArray[(0)*sizeof(Type)+ ParentClass::GetHeaderOffset() ]);
00569             }
00570         #endif
00571             return (Type &)(ParentClass::mBaseArray[(pIndex)*sizeof(Type)+ ParentClass::GetHeaderOffset() ]);
00572         }
00573 
00575         inline void SetAt(int pIndex, Type pItem)
00576         {
00577         #if defined(_DEBUG) && !defined(KARCH_ENV_MACOSX)
00578             if (!ParentClass::ValidateIndex( pIndex ))
00579             {
00580                 return;
00581             }
00582         #endif
00583             GetArray()[pIndex] = pItem;
00584         }
00585 
00587         inline void SetLast(Type pItem)
00588         {
00589             SetAt (ParentClass::GetArrayCount()-1, pItem);
00590         }
00591 
00593         inline Type GetAt(int pIndex) const
00594         {
00595         #if defined(_DEBUG) && !defined(KARCH_ENV_MACOSX)
00596             if (!ParentClass::ValidateIndex( pIndex ))
00597             {
00598                 return (Type &)(ParentClass::mBaseArray[(0)*sizeof(Type)+ ParentClass::GetHeaderOffset() ]);
00599             }
00600         #endif
00601             return (Type &)(ParentClass::mBaseArray[(pIndex)*sizeof(Type)+ ParentClass::GetHeaderOffset() ]);
00602         }
00603 
00607         inline Type GetFirst() const
00608         {
00609         #ifndef KFBX_PLUGIN
00610             K_ASSERT( ParentClass::GetArrayCount() >= 1 );
00611         #endif
00612             return GetAt(0);
00613         }
00614 
00618         inline Type GetLast() const
00619         {
00620         #ifndef KFBX_PLUGIN
00621             K_ASSERT( ParentClass::GetArrayCount() >= 1 );
00622         #endif
00623             return GetAt(ParentClass::GetArrayCount()-1);
00624         }
00625 
00630         inline int Find(Type pItem) const
00631         {
00632             return FindAfter( -1, pItem );
00633         }
00634 
00640         inline int FindAfter(int pAfterIndex, Type pItem) const
00641         {
00642         #ifndef KFBX_PLUGIN
00643         #ifdef _DEBUG
00644             if ( pAfterIndex > ParentClass::GetArrayCount() || pAfterIndex < -1 )
00645             {
00646                 K_ASSERT_MSG_NOW (_T("ArrayUL : Search Begin Index out of range"));
00647                 return -1;
00648             }
00649         #endif
00650         #endif
00651             int Count;
00652             for ( Count=pAfterIndex+1; Count<ParentClass::GetArrayCount(); Count++)
00653             {
00654                 if (GetAt(Count)==pItem)
00655                 {
00656                     return Count;
00657                 }
00658             }
00659             return -1;
00660         }
00661 
00667         inline int FindBefore(int pBeforeIndex, Type pItem) const
00668         {
00669         #ifndef KFBX_PLUGIN
00670         #ifdef _DEBUG
00671             if ( pBeforeIndex > ParentClass::GetArrayCount() || pBeforeIndex <= 0 )
00672             {
00673                 K_ASSERT_MSG_NOW (_T("ArrayUL : Search Begin Index out of range"));
00674                 return -1;
00675             }
00676         #endif
00677         #endif
00678             int Count;
00679             for ( Count=pBeforeIndex-1; Count>=0; Count--)
00680             {
00681                 if (GetAt(Count)==pItem)
00682                 {
00683                     return Count;
00684                 }
00685             }
00686             return -1;
00687         }
00688 
00692         inline int Add(Type pItem)
00693         {
00694             return InsertAt(ParentClass::GetArrayCount(), pItem);
00695         }
00696 
00700         inline int AddUnique(Type pItem)
00701         {
00702             int lReturnIndex = Find(pItem);
00703             if (lReturnIndex == -1)
00704             {
00705                 lReturnIndex = Add(pItem);
00706             }
00707             return lReturnIndex;
00708         }
00709 
00713         inline void AddMultiple( kUInt pItemCount )
00714         {
00715             ParentClass::AddMultiple( pItemCount );
00716         }
00717 
00718         inline void AddArray(KArrayTemplate<Type> &pArray)
00719         {
00720             int lSourceIndex, lCount = pArray.GetCount();
00721             if( lCount == 0 ) return;
00722             int lDestinationIndex = ParentClass::GetCount();
00723             AddMultiple(lCount);
00724             for( lSourceIndex = 0; lSourceIndex < lCount; lSourceIndex++)
00725             {
00726                 SetAt(lDestinationIndex++, pArray[lSourceIndex]);
00727             }
00728         }
00729 
00730         inline void AddArrayNoDuplicate(KArrayTemplate<Type> &pArray)
00731         {
00732             int i, lCount = pArray.GetCount();
00733             for( i = 0; i < lCount; i++)
00734             {
00735                 Type lItem = pArray[i];
00736                 if (Find(lItem) == -1)
00737                 {
00738                     Add(lItem);
00739                 }
00740             }
00741         }
00742         inline void RemoveArray(KArrayTemplate<Type> &pArray)
00743         {
00744             int lRemoveIndex, lRemoveCount = pArray.GetCount();
00745             for( lRemoveIndex = 0; lRemoveIndex < lRemoveCount; lRemoveIndex++)
00746             {
00747                 RemoveIt(pArray[lRemoveIndex]);
00748             }
00749         }
00750 
00752         inline Type* GetArray() const
00753         {
00754             if (ParentClass::mBaseArray == NULL)
00755                 return NULL;
00756 
00757             return (Type*)(ParentClass::mBaseArray+ ParentClass::GetHeaderOffset()) ;
00758         }
00759 
00761         inline KArrayTemplate<Type>& operator=(const KArrayTemplate<Type>& pArrayTemplate)
00762         {
00763             ParentClass::Clear();
00764 
00765             int i, lCount = pArrayTemplate.GetCount();
00766 
00767             for (i = 0; i < lCount; i++)
00768             {
00769                 Add(pArrayTemplate[i]);
00770             }
00771 
00772             return (*this);
00773         }
00774 
00775         #ifdef KFBX_PLUGIN
00777             inline operator Type* ()
00778             {
00779                 return GetArray();
00780             }
00781         #endif
00782     };
00783 
00785     //
00786     //  WARNING!
00787     //
00788     //  Anything beyond these lines may not be documented accurately and is
00789     //  subject to change without notice.
00790     //
00792 
00793     #ifndef DOXYGEN_SHOULD_SKIP_THIS
00794 
00795     template <class Type> inline void DeleteAndClear(KArrayTemplate<Type>& Array)
00796     {
00797         kUInt lItemCount = Array.GetCount();
00798         while( lItemCount )
00799         {
00800             lItemCount--;
00801             Type& Item = (Array.operator[](lItemCount));
00802             delete Item;
00803             Item = NULL;
00804         }
00805         Array.Clear();
00806     }
00807 /*    template <class Type> inline void DeleteAndClear(KArrayTemplate<Type>& Array)
00808     {
00809         kUInt lItemCount = Array.GetCount();
00810         while( lItemCount )
00811         {
00812             lItemCount--;
00813             Type& Item = (Array.operator[](lItemCount));
00814             delete Item;
00815             Item = NULL;
00816         }
00817         Array.Clear();
00818     }
00819 */
00820     typedef class KFBX_DLL KArrayTemplate<int *>    KArrayHkInt;
00821     typedef class KFBX_DLL KArrayTemplate<kUInt *>  KArrayHkUInt;
00822     typedef class KFBX_DLL KArrayTemplate<double *> KArrayHkDouble;
00823     typedef class KFBX_DLL KArrayTemplate<float *>  KArrayHkFloat;
00824     typedef class KFBX_DLL KArrayTemplate<void *>   KArrayVoid;
00825     typedef class KFBX_DLL KArrayTemplate<char *>   KArrayChar;
00826     typedef class KFBX_DLL KArrayTemplate<int>      KArraykInt;
00827     typedef class KFBX_DLL KArrayTemplate<kUInt>    KArraykUInt;
00828     typedef class KFBX_DLL KArrayTemplate<float>    KArraykFloat;
00829     typedef class KFBX_DLL KArrayTemplate<double>   KArraykDouble;
00830 
00831     typedef class KFBX_DLL KArrayTemplate<kReference>   KArrayUL;
00832 
00833     #endif // #ifndef DOXYGEN_SHOULD_SKIP_THIS
00834 
00835 #include <fbxfilesdk/fbxfilesdk_nsend.h>
00836 
00837 #endif // FBXFILESDK_COMPONENTS_KBASELIB_KLIB_KARRAYUL_H
00838