小弟用了一个封装的ADO类访问MySQL数据库,在存8位灰度bmp图像文件时出现问题。
bmp文件的大小是2622518 Byte,可是存到数据库中却是2622644 Byte,多了126 byte. 再用数据库的客户端把字段存为文件,得到的图像和原图不同,高亮度区的颜色变成了黄色,左侧一窄条上下颠倒显示,这是怎么回事呢?请高手帮忙分析分析,多谢多谢!附相关部分源代码:
加载BMP文件到内存:
CFile file;
         file.Open( pBMPPathname, CFile::modeRead) )
m_nFileLen = file.GetLength();
m_pBMPBuffer = new BYTE[m_nFileLen + 1];
写入数据库:
CADORecordset newSet(&m_DB);
newSet.AppendChunk("data",m_pBMPBuffer, m_nFileLen);
ADO类函数:
BOOL CADORecordset::AppendChunk(LPCTSTR lpFieldName, LPVOID lpData, UINT nBytes)
{ FieldPtr pField = m_pRecordset->Fields->GetItem(lpFieldName); return AppendChunk(pField, lpData, nBytes);
}BOOL CADORecordset::AppendChunk(FieldPtr pField, LPVOID lpData, UINT nBytes)
{
HRESULT hr;
_variant_t varChunk;
long lngOffset = 0;
UCHAR chData;
SAFEARRAY FAR *psa = NULL;
SAFEARRAYBOUND rgsabound[1]; try
{
//Create a safe array to store the array of BYTES 
rgsabound[0].lLbound = 0;
rgsabound[0].cElements = nBytes;
psa = SafeArrayCreate(VT_UI1,1,rgsabound);
        
while(lngOffset < (long)nBytes)
{
chData = ((UCHAR*)lpData)[lngOffset];
hr = SafeArrayPutElement(psa, &lngOffset, &chData); if(FAILED(hr))
return FALSE;

lngOffset++;
}
lngOffset = 0; //Assign the Safe array  to a variant. 
varChunk.vt = VT_ARRAY|VT_UI1;
varChunk.parray = psa; hr = pField->AppendChunk(varChunk); if(SUCCEEDED(hr))
return TRUE;
}
catch(_com_error &e)
{
dump_com_error(e);
return FALSE;
} return FALSE;
}

解决方案 »

  1.   

    现在又知道了多写了哪些字节,8bit位图的调色板的0x81~0xFE索引的reserve字段0x00被写成了 0x5C 0x30,这样正好多了126个字节(也就是说,应该是81 81 81 00 82 82 82 00 …… FD FD FD 00 FE FE FE 00, 却被存成了 81 81 81 5C 30 82 82 82 5C 30 ……FD FD FD 5C 30 FE FE FE 5C 30)。5C 30 的ascii 分别是'\0' 和 '0',为什么会被改变了呢?问题描述中的“左侧一窄条上下颠倒显示”不对,应该是图像右侧的126像素宽的块显示到了左边,这些都可以用上一段话解释,颜色显示不正常现象也可以解释。可是问题是:为什么会出现第一段的现象,00被换成了5C 30?为什么还有130个00 没有被换成5C 30?? 问题出在何处???应该如何修改????我的m_pBMPBuffer使用的是LPBYTE. 跟踪到ado写入之前,写入长度都等于m_nFileLen,MySQL中的字段类型为MEDIUMBLOB。还请高人指教。