⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 xbytebuffer.cpp

📁 BCB的学习资料
💻 CPP
📖 第 1 页 / 共 4 页
字号:
//---------------------------------------------------------------------------


#pragma hdrstop

#include "XByteBuffer.h"

//---------------------------------------------------------------------------

#pragma package(smart_init)
namespace zdhsoft
{
/*
////////////////////////////////////////////////////////////////////////////////
[Name]XByteBuffer
[Title]XByteBuffer的构造函数
////////////////////////////////////////////////////////////////////////////////
[Param]
    <int default=XBYTE_BUFFER_MIN_BLOCK>iPrepareLength 初始要准备的空间
[Exception]
    EOutOfMemory 如果申请内存,则抛出该异常
[Description]
    构造函数,需要指定准备分配的空间的大小,默认为XBYTE_BUFFER_MIN_BLOCK
[Version]1.0
[Author]Rex Winter
[Date]2005-6-18
////////////////////////////////////////////////////////////////////////////////
*/
XByteBuffer::XByteBuffer(int iPrepareLength)
    :m_DataSize(0),
     m_Length(0),
     m_Data(NULL)
{
    iPrepareLength = PrepareLength(iPrepareLength);
    m_Data = new XByte[iPrepareLength];
    if( m_Data == NULL ) throw EOutOfMemory(EXCEPTION_OUT_OF_MEMORY);
    m_DataSize = iPrepareLength;
}
/*
////////////////////////////////////////////////////////////////////////////////
[Name]XByteBuffer
[Title]XByteBuffer的构造函数
////////////////////////////////////////////////////////////////////////////////
[Param]
    <void *>aData 要被复制的数据
    <int> aDataSize 要被复制的数据的字节数
    <int default=XBYTE_BUFFER_MIN_BLOCK>iPrepareLength 初始要准备的空间
[Exception]
    EOutOfMemory 如果申请内存,则抛出该异常
[Description]
    构造函数,需要指定准备分配的空间的大小,默认为XBYTE_BUFFER_MIN_BLOCK
[Version]1.0
[Author]Rex Winter
[Date]2005-6-18
////////////////////////////////////////////////////////////////////////////////
*/
XByteBuffer::XByteBuffer(void * aData,int aDataSize,int iPrepareLength)
    :m_DataSize(0),
     m_Length(0),
     m_Data(NULL)
{
    iPrepareLength = PrepareLength( (iPrepareLength>aDataSize)?iPrepareLength:aDataSize );
    m_Data = new XByte[iPrepareLength];
    if( m_Data == NULL ) throw EOutOfMemory(EXCEPTION_OUT_OF_MEMORY);
    m_DataSize = iPrepareLength;
    if( aDataSize > 0 )
    {
        memcpy(m_Data,aData, aDataSize);
        m_Length = aDataSize;
    }
}
/*
////////////////////////////////////////////////////////////////////////////////
[Name]XByteBuffer
[Title]XByteBuffer的拷贝构造函数
////////////////////////////////////////////////////////////////////////////////
[Param]
    <const XByteBuffer &>aBuffer 被复制的对象
[Exception]
    EOutOfMemory 如果申请内存,则抛出该异常
[Description]
    拷贝构造函数,分配的空间是实际需要的最小空间。
[Version]1.0
[Author]Rex Winter
[Date]2005-6-18
////////////////////////////////////////////////////////////////////////////////
*/
XByteBuffer::XByteBuffer(const XByteBuffer & aBuffer)
    :m_DataSize(0),
     m_Length(aBuffer.m_Length),
     m_Data(NULL)
{
    int iPrepareLength = PrepareLength(m_Length);
    m_Data = new XByte[iPrepareLength];
    if( m_Data == NULL ) throw EOutOfMemory(EXCEPTION_OUT_OF_MEMORY);
    m_DataSize = iPrepareLength;
    memcpy(m_Data,aBuffer.m_Data,m_Length);
}
/*
////////////////////////////////////////////////////////////////////////////////
[Name]XByteBuffer
[Title]XByteBuffer的析构函数
////////////////////////////////////////////////////////////////////////////////
[Param]
[Exception]
[Description]
    析构函数
[Version]1.0
[Author]Rex Winter
[Date]2005-6-18
////////////////////////////////////////////////////////////////////////////////
*/
XByteBuffer::~XByteBuffer()
{
    if( m_Data != NULL ) delete[] m_Data;
}

/*
////////////////////////////////////////////////////////////////////////////////
[Name]operator[]
[Title]下标操作符
////////////////////////////////////////////////////////////////////////////////
[Param]
    <int> Index 下标值
[Return]
    <XByte &>返回XByte类型的引用
[Exception]
    XExceptionArrayOutOfRange 如果下标越界,则抛出该异常
[Description]
    下标操作符
[Version]1.0
[Author]Rex Winter
[Date]2005-6-21
////////////////////////////////////////////////////////////////////////////////
*/
XByte & XByteBuffer::operator[](int Index)
{
    if( Index<0 || Index >= m_Length ) throw XExceptionArrayOutOfRange(Index, m_Length);
    return m_Data[Index];
}
/*
////////////////////////////////////////////////////////////////////////////////
[Name]operator[]
[Title]下标操作符
////////////////////////////////////////////////////////////////////////////////
[Param]
    <int> Index 下标值
[Return]
    <const XByte &>返回XByte类型的引用
[Exception]
    XExceptionArrayOutOfRange 如果下标越界,则抛出该异常
[Description]
    下标操作符
[Version]1.0
[Author]Rex Winter
[Date]2005-6-21
////////////////////////////////////////////////////////////////////////////////
*/
const XByte & XByteBuffer::operator[] (int Index) const
{
    if( Index<0 || Index >= m_Length ) throw XExceptionArrayOutOfRange(Index, m_Length);
    return m_Data[Index];
}
/*
////////////////////////////////////////////////////////////////////////////////
[Name]expandCapacity
[Title]扩充缓冲区容量
////////////////////////////////////////////////////////////////////////////////
[Param]
    <int> minimumCapacity 最小所需的容量
    <bool default = true> 是否要copy原数据,true表示Copy原数据,false表示不再copy
[Return]
    void
[Exception]
    EOutOfMemory 如果申请缓冲区失败,那么则抛出该异常
[Description]
    扩充缓冲区容量,如果扩充前的数据是有用的,那么这些数据在扩充容量后Copy到新缓冲区中
[Version]1.0
[Author]Rex Winter
[Date]2005-6-21
////////////////////////////////////////////////////////////////////////////////
*/
void XByteBuffer::expandCapacity(int minimumCapacity,bool bCopyData)
{
    int newCapacity = m_DataSize * 2;
    if (newCapacity < 0)  newCapacity = 0x7fffff;//最大32位正整数
    else if (minimumCapacity > newCapacity) newCapacity = minimumCapacity;
    int iPrepareLength = PrepareLength(newCapacity);
    XByte * tmp = new XByte[iPrepareLength];
    if( tmp == NULL ) throw EOutOfMemory(EXCEPTION_OUT_OF_MEMORY);
    if( bCopyData )
    {
        if( m_Length > 0 ) memcpy(tmp, m_Data, m_Length);
    }
    else
    {
        m_Length = 0;
    }
    delete[] m_Data;
    m_DataSize = iPrepareLength;
    m_Data = tmp;
}
/*
////////////////////////////////////////////////////////////////////////////////
[Name]operaotr=
[Title]缓冲区对象的赋值运算符
////////////////////////////////////////////////////////////////////////////////
[Param]
    <const XByteBuffer &> aBuffer 赋值的目标缓冲区
[Return]
    XByteBuffer & 当前对象的引用
[Exception]
    EOutOfMemory 如果申请缓冲区失败,那么则抛出该异常
[Description]
    重载赋值操作,避免编译器产生一个缺省的
[Version]1.0
[Author]Rex Winter
[Date]2005-6-21
////////////////////////////////////////////////////////////////////////////////
*/

XByteBuffer & XByteBuffer::operator=(const XByteBuffer & aBuffer)
{
    if(this == &aBuffer) return * this;
    if( aBuffer.m_Length > m_DataSize )
    {
        expandCapacity( aBuffer.m_Length ,false); //因为原有的数据全不要了,所以重新分配内存的时候,不需要再copy
    }
    memcpy(m_Data,aBuffer.m_Data,aBuffer.m_Length);
    m_Length = aBuffer.m_Length;
    return *this;
}
/*
////////////////////////////////////////////////////////////////////////////////
[Name]Clear
[Title]清空缓冲区的数据
////////////////////////////////////////////////////////////////////////////////
[Param]
    <bool default = false> bFree 释放现有缓冲区标志,如果为true表示释放当前的缓冲区,否则不释放
[Return]
    void
[Exception]
    EOutOfMemory 如果申请缓冲区失败,那么则抛出该异常
[Description]
    清空缓冲区的数据,如果bFree为true表示释放当前缓冲区,并重新申请一块缓冲区
[Version]1.0
[Author]Rex Winter
[Date]2005-6-21
////////////////////////////////////////////////////////////////////////////////
*/
void XByteBuffer::Clear(bool bFree)
{
    if(bFree)
    {
        if( m_DataSize != XBYTE_BUFFER_MIN_BLOCK )
        {
            delete[] m_Data;
            m_Data = new XByte[XBYTE_BUFFER_MIN_BLOCK];
            if( m_Data == NULL ) throw EOutOfMemory(EXCEPTION_OUT_OF_MEMORY);
            m_DataSize = XBYTE_BUFFER_MIN_BLOCK;
        }
    }
    m_Length = 0;
}
/*
////////////////////////////////////////////////////////////////////////////////
[Name]Append...Array
[Title]向缓冲区中追加一个数组的元素
////////////////////////////////////////////////////////////////////////////////
[Param]
    <const XArray<...>&  > aArray 被追加的数组
    或者是
    <const XDynamicArray<...>& > aArray被追回的数组
[Return]
    <XByteBuffer &>返回当前缓冲区的引用
[Exception]
    EOutOfMemory 如果申请缓冲区失败,那么则抛出该异常
[Description]
    向缓冲区中追加一个数组的元素,这些方法包括
    AppendByteArray,AppendCharArray ...等一组这样的方法
[Version]1.0
[Author]Rex Winter
[Date]2005-6-21
////////////////////////////////////////////////////////////////////////////////
*/

XByteBuffer & XByteBuffer::AppendByteArray(const XArray<XByte> &aByteArray)
{
    int ArrayLength = aByteArray.GetLength();
    if( ArrayLength > 0 )
    {
        ensureCapacity( m_Length + ArrayLength );
        XByte * dest = m_Data + m_Length;
        const XByte * src = aByteArray.Data();
        for(int i=0; i<ArrayLength; i++) *dest++ = *src++;
//这段汇编等同于上同的for,为了移植性,就不采用汇编了
//        asm
//        {
//            mov ecx, ArrayLength
//            mov ebx, src
//            mov edx, dest
//
//            @NEXT_COPY:
//            cmp ecx,0
//            jz  near @COPY_OK
//            mov al,byte ptr [ebx]
//            mov byte ptr [edx],al
//            inc ebx
//            inc edx
//            dec ecx
//            jmp near @NEXT_COPY
//
//            @COPY_OK:
//        }
        m_Length += ArrayLength;
    }
    return *this;
}
XByteBuffer & XByteBuffer::AppendCharArray(const XArray<XChar> &aCharArray)
{
    int ArrayLength = aCharArray.GetLength();
    if( ArrayLength > 0 )
    {
        ensureCapacity( m_Length + ArrayLength );
        XByte * dest = m_Data + m_Length;
        const XByte * src = (const XByte *)aCharArray.Data();

        for(int i=0; i<ArrayLength; i++) *dest++ = *src++;

        m_Length += ArrayLength;
    }
    return *this;

}
XByteBuffer & XByteBuffer::AppendBoolArray(const XArray<XBoolean> &aBoolArray)
{
    int ArrayLength = aBoolArray.GetLength();
    if( ArrayLength > 0 )
    {
        ensureCapacity( m_Length + ArrayLength );
        XByte * dest = m_Data + m_Length;
        const XBoolean * src = aBoolArray.Data();

        for(int i=0; i<ArrayLength; i++)
        {
            if( *src ) *dest++ = 1;
            else *dest++ = 0;
            src++;
        }
        m_Length += ArrayLength;
    }
    return *this;
}
XByteBuffer & XByteBuffer::AppendBuffer(const XByteBuffer & aBuffer)
{
    int ArrayLength = aBuffer.GetLength();
    if( ArrayLength > 0 )
    {
        ensureCapacity( m_Length + ArrayLength );
        XByte * dest = m_Data + m_Length;
        const XByte * src = aBuffer.m_Data;
        for(int i=0; i<ArrayLength; i++) *dest++ = *src++;
        m_Length += ArrayLength;
    }
    return *this;
}
XByteBuffer & XByteBuffer::AppendShortArray(const XArray<XShort> &aShortArray)
{
    int ArrayLength = aShortArray.GetLength();
    if( ArrayLength > 0 )
    {
        ensureCapacity( m_Length + ArrayLength * 2 );
        XByte * dest = m_Data + m_Length;
        const XByte * src = (const XByte *)aShortArray.Data();
        for(int i=0; i<ArrayLength; i++)
        {
            *dest++= *(src+1);
            *dest++ = *src++;
            src++;
        }
        m_Length += ArrayLength * 2;
    }
    return *this;
}
XByteBuffer & XByteBuffer::AppendWordArray(const XArray<XWord> &aWordArray)
{
    int ArrayLength = aWordArray.GetLength();
    if( ArrayLength > 0 )
    {
        ensureCapacity( m_Length + ArrayLength * 2 );

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -