2010-11-03 22:02
论坛为什么逼着我结贴的?
路过的大侠,有时间帮检查或改良下述实现.不胜感激!
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
CVDT::CVDT():m_pData(NULL){
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// 〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓
/////////////////////////////////////////////////////////////////////////////////////////////////////////
char* CVDT::AllocBuffer(UINT iDataLen)
{
if (m_pData==NULL){
m_pData = new char[16+iDataLen];
}else if(iDataLen>((UINT*)m_pData)[2]){
if (((UINT*)m_pData)[0]==1){
delete []m_pData;
}else{
((UINT*)m_pData)[0]-=1;
}
m_pData = new char[16+iDataLen];
}else{
if (((UINT*)m_pData)[0]!=1){
((UINT*)m_pData)[0]-=1;
m_pData = new char[16+iDataLen];
}
}
/////////////////////////////////////////////////////////////////////////////////////////////////////
((UINT*)m_pData)[0] = 1;
/////////////////////////////////////////////////////////////////////////////////////////////////////
((UINT*)m_pData)[1] = 0;
((UINT*)m_pData)[2] =((UINT*)m_pData)[3] = iDataLen;
/////////////////////////////////////////////////////////////////////////////////////////////////////
if (iDataLen==0){ return NULL; }
/////////////////////////////////////////////////////////////////////////////////////////////////////
return m_pData + 16;
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// 〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓
/////////////////////////////////////////////////////////////////////////////////////////////////////////
CVDT::CVDT(const char* pSet,UINT iDataLen,bool bZip):m_pData(NULL){
char* pBuffer;
if (pBuffer=AllocBuffer(iDataLen)){
if (pSet){ memcpy(pBuffer,pSet,iDataLen); }
if (bZip){ ZipIt(); }
}
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// 〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓
/////////////////////////////////////////////////////////////////////////////////////////////////////////
CVDT::CVDT(const CVDT& vSet):m_pData(NULL){
if (vSet.m_pData){
m_pData = vSet.m_pData;
((UINT*)m_pData)[0]+=1;
}
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
CVDT::~CVDT(){
if (m_pData){
if (((UINT*)m_pData)[0]==1){
delete []m_pData; m_pData = NULL;
}else{
((UINT*)m_pData)[0]-=1;
}
}
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
const char* CVDT::GetVDTStream(){
if (m_pData==NULL){ AllocBuffer(0); }
return m_pData;
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
char* CVDT::GetData(){
if (m_pData && ((UINT*)m_pData)[2]>0){
if (((UINT*)m_pData)[0]==1){
return m_pData + 16;
}else{
char* pTm = m_pData; ((UINT*)pTm)[0]-=1;
char* pBuffer = AllocBuffer(((UINT*)pTm)[2]);
if (pBuffer){
memcpy(m_pData,pTm,((UINT*)pTm)[2]+16);
((UINT*)m_pData)[0] = 1;
return m_pData + 16;
}else{
return NULL;
}
}
}
/////////////////////////////////////////////////////////////////////////////////////////////////////
return NULL;
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
const char* CVDT::GetDataConst(){
if (m_pData && ((UINT*)m_pData)[2]>0){ return m_pData + 16; }
return NULL;
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
const char* CVDT::GetString(){
if (m_pData && ((UINT*)m_pData)[2]>0){
UnZipIt();
const char* pRet = GetDataConst();
if (pRet){ return pRet; }else{ return ""; }
}else{ return ""; }
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
void CVDT::GetStringArray(CStringArray& cSArray)
{
if (m_pData && ((UINT*)m_pData)[2]>0){
UnZipIt();
cSArray.RemoveAll();
/////////////////////////////////////////////////////////////////////////////////////////////////
const char* pStart = GetDataConst();
if (!pStart){ return; }
/////////////////////////////////////////////////////////////////////////////////////////////////
UINT iCount = *((UINT*)pStart);
pStart += sizeof(UINT);
cSArray.SetSize(iCount);
for (UINT I=0; I<iCount; I++){
UINT iSLen = *((UINT*)pStart); pStart += sizeof(UINT);
cSArray[I]
= pStart;
pStart += iSLen;
}
}
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
UINT CVDT::GetTotalSize(){
if (m_pData){ return ((UINT*)m_pData)[2]+16; }
/////////////////////////////////////////////////////////////////////////////////////////////////////
return 0;
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
UINT CVDT::GetDataSize(){
if (m_pData){ return ((UINT*)m_pData)[2]; }
/////////////////////////////////////////////////////////////////////////////////////////////////////
return 0;
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
void CVDT::operator = (const CVDT& rSrc)
{
if (rSrc.m_pData){
if (m_pData){
if (((UINT*)m_pData)[0]==1){
delete []m_pData;
}else{
((UINT*)m_pData)[0]-=1;
}
}
/////////////////////////////////////////////////////////////////////////////////////////////////
m_pData = rSrc.m_pData;
((UINT*)m_pData)[0]+=1;
}
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
void CVDT::ReadInFromFile(CFile& file)
{
UINT i1Flags,i2Flags,iZipLen,iUnZipLen;
file.Read(&i1Flags,
4);
file.Read(&i2Flags,
4);
file.Read(&iZipLen,
4);
file.Read(&iUnZipLen,4);
/////////////////////////////////////////////////////////////////////////////////////////////////////
char* pBuf;
if (pBuf = AllocBuffer(iZipLen)){
file.Read(pBuf,iZipLen);
}
/////////////////////////////////////////////////////////////////////////////////////////////////////
((UINT*)m_pData)[0] = i1Flags;
((UINT*)m_pData)[1] = i2Flags;
((UINT*)m_pData)[2] = iZipLen;
((UINT*)m_pData)[3] = iUnZipLen;
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
void CVDT::ReadInFromStream(const char*& pIn)
{
UINT i1Flags
=((UINT*)pIn)[0];
UINT i2Flags
=((UINT*)pIn)[1];
UINT iZipLen
=((UINT*)pIn)[2];
UINT iUnZipLen =((UINT*)pIn)[3];
/////////////////////////////////////////////////////////////////////////////////////////////////////
char* pBuf;
pIn += 16;
if (pBuf = AllocBuffer(iZipLen)){
memcpy(pBuf,pIn,iZipLen); pIn += iZipLen;
}
/////////////////////////////////////////////////////////////////////////////////////////////////////
((UINT*)m_pData)[0] = i1Flags;
((UINT*)m_pData)[1] = i2Flags;
((UINT*)m_pData)[2] = iZipLen;
((UINT*)m_pData)[3] = iUnZipLen;
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
void CVDT::WriteOutToFile(CFile& file)
{
UINT iDataLen;
if (m_pData && (iDataLen=((UINT*)m_pData)[2])>0){
file.Write(m_pData,iDataLen+16);
}else{
UINT iHeads[4] = {0,0,0,0};
file.Write(&iHeads,16);
}
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
void CVDT::SetStringArray(CStringArray& sArray,bool bZip)
{
UINT iLAllStrings = 0; UINT
iCount = sArray.GetSize();
/////////////////////////////////////////////////////////////////////////////////////////////////////
for (UINT I=0; I<iCount; I++){
iLAllStrings += (strlen(sArray[I])+1);
}
/////////////////////////////////////////////////////////////////////////////////////////////////////
if (iCount==0){
UINT
iDataLen = sizeof(UINT);
char* pBuffer
= AllocBuffer(iDataLen);
if (pBuffer){ memcpy(pBuffer,&iCount,iDataLen); }
}else{
/////////////////////////////////////////////////////////////////////////////////////////////////
UINT
iFullDataLen = sizeof(UINT) + iCount*sizeof(UINT) + iLAllStrings;
char* pBuffer
= AllocBuffer(iFullDataLen);
/////////////////////////////////////////////////////////////////////////////////////////////////
if (!pBuffer){ return; }
/////////////////////////////////////////////////////////////////////////////////////////////////
*((UINT*)pBuffer) = iCount; pBuffer += sizeof(UINT);
/////////////////////////////////////////////////////////////////////////////////////////////////
for (UINT I=0; I<iCount; I++){
UINT iStrLen = strlen(sArray[I])+1;
*((UINT*)pBuffer) = iStrLen;
pBuffer += sizeof(UINT);
/////////////////////////////////////////////////////////////////////////////////////////////
strcpy(pBuffer,sArray[I]); pBuffer += iStrLen;
}
}
/////////////////////////////////////////////////////////////////////////////////////////////////////
if (bZip){ ZipIt(); }
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
void CVDT::UnZipIt()
{
uLong iLZipped;
if (m_pData && (iLZipped=((uLong*)m_pData)[2])>0 && (((uLong*)m_pData)[1] & FLAG_ZIPPED)){
uLong iLUnZipped
=((uLong*)m_pData)[3];
uLong iNewTotalLen
= 16+iLUnZipped;
/////////////////////////////////////////////////////////////////////////////////////////////////
char* pBuffer = new char[iNewTotalLen];
Byte* pDest
= (Byte*)(pBuffer+16);
Byte* pSour
= (Byte*)(m_pData+16);
/////////////////////////////////////////////////////////////////////////////////////////////////
uncompress(pDest,&iLUnZipped,pSour,iLZipped);
/////////////////////////////////////////////////////////////////////////////////////////////////
((uLong*)pBuffer)[0] = 1;
((uLong*)pBuffer)[1] = ((uLong*)m_pData)[1] & ~FLAG_ZIPPED;
((uLong*)pBuffer)[2] = iLUnZipped;
((uLong*)pBuffer)[3] = iLUnZipped;
/////////////////////////////////////////////////////////////////////////////////////////////////
if (((UINT*)m_pData)[0]==1){
delete []m_pData;
}else{
((UINT*)m_pData)[0]-=1;
}
/////////////////////////////////////////////////////////////////////////////////////////////////
m_pData = pBuffer;
}
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////
void CVDT::ZipIt()
{
uLong iDataLen;
if (m_pData && (iDataLen=((uLong*)m_pData)[2])>0 && !(((uLong*)m_pData)[1] & FLAG_ZIPPED)){
uLong iLZipped
= iDataLen + 240;
uLong iLUnZipped = iDataLen;
/////////////////////////////////////////////////////////////////////////////////////////////////
char* pBuffer = new char[16+iLZipped];
Byte* pDest
= (Byte*)(pBuffer+16);
Byte* pSour
= (Byte*)(m_pData+16);
/////////////////////////////////////////////////////////////////////////////////////////////////
compress(pDest,&iLZipped,pSour,iLUnZipped);
/////////////////////////////////////////////////////////////////////////////////////////////////
((uLong*)pBuffer)[0] = 1;
((uLong*)pBuffer)[1] =((uLong*)m_pData)[1]|FLAG_ZIPPED;
((uLong*)pBuffer)[2] = iLZipped;
((uLong*)pBuffer)[3] = iLUnZipped;
/////////////////////////////////////////////////////////////////////////////////////////////////
if (((UINT*)m_pData)[0]==1){
delete []m_pData;
}else{
((UINT*)m_pData)[0]-=1;
}
/////////////////////////////////////////////////////////////////////////////////////////////////
m_pData = pBuffer;
}
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////
// ●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●●
/////////////////////////////////////////////////////////////////////////////////////////////////////////