关于用VC,VB进行图像数据(二进制大对象)存储数据库的一点心得

原创 2001年05月05日 16:05:00

       网上经常有人问如何把图像存入数据库中,原先我也是不得要领。经过多方指点和自己在开发过程中的摸索,终于解决这一问题。

       下面给出用VC,VB如何操作图像文件存取数据库的原码,帮助一些还没有掌握方法的朋友,也请这方面的高手多多指教。(均用ADO连接数据库)

1. VC把一个文件存入数据库

  CFile imagefile;
  if(0 == imagefile.Open("d://user//bmp.bmp",CFile::modeRead))
     return;
  _RecordsetPtr pRs = NULL;             
  _ConnectionPtr pConnection = NULL;
  _variant_t varChunk;
  HRESULT hr;
  BYTE* pbuf;
  long nLength = imagefile.GetLength();
  pbuf = new BYTE[nLength+2];
  if(pbuf == NULL)
     return;                             //allocate memory error;
  imagefile.Read(pbuf,nLength);          //read the file into memory

  BYTE *pBufEx;
  pBufEx = pbuf;
  //build a SAFFERRAY
  SAFEARRAY* psa;
  SAFEARRAYBOUND rgsabound[1];
  rgsabound[0].lLbound = 0;
  rgsabound[0].cElements = nLength;
  psa = SafeArrayCreate(VT_UI1, 1, rgsabound);

  for (long i = 0; i < nLength; i++)
       SafeArrayPutElement (psa, &i, pBufEx++);
  VARIANT varBLOB;
  varBLOB.vt = VT_ARRAY | VT_UI1;
  varBLOB.parray = psa;

  _bstr_t strCnn("Provider=SQLOLEDB.1;Integrated Security=SSPI;Persist Security Info=False;Initial Catalog=CUSTOM;Data Source=SERVER");   
    try
    {
        //Open a connection
        pConnection.CreateInstance(__uuidof(Connection));
        hr = pConnection->Open(strCnn,"","",NULL);   //Connect a DataBase
        pRs.CreateInstance(__uuidof(Recordset));
        pRs->Open("CustomInfo",_variant_t((IDispatch *) pConnection,true),adOpenKeyset,adLockOptimistic,adCmdTable);  //Open a Table
 
//      pRs->AddNew();       
        pRs->Fields->GetItem("Image")->AppendChunk(varBLOB);       
        pRs->Update();
        pRs->Close();
        pConnection->Close();
 }
    catch(_com_error &e)
    {
        // Notify the user of errors if any.
        _bstr_t bstrSource(e.Source());
        _bstr_t bstrDescription(e.Description());
        CString sError;
        sError.Format("Source : %s /n Description : %s/n",(LPCSTR)bstrSource,(LPCSTR)bstrDescription);
        AfxMessageBox(sError);    
 }

2. VC把数据库中IMAGE字段取出存为文件

    _RecordsetPtr pRs = NULL;
    _ConnectionPtr pConnection = NULL;
    _variant_t varChunk;
    HRESULT hr;
    VARIANT varBLOB;
    _bstr_t strCnn("Provider=SQLOLEDB.1;Integrated Security=SSPI;Persist Security Info=False;Initial Catalog=CUSTOM;Data Source=SERVER");   
    try
    {
        //Open a connection
        pConnection.CreateInstance(__uuidof(Connection));
        hr = pConnection->Open(strCnn,"","",NULL);       
        pRs.CreateInstance(__uuidof(Recordset));
        pRs->Open("CustomInfo",_variant_t((IDispatch *) pConnection,true),adOpenKeyset,adLockOptimistic,adCmdTable);
       //read  data  
       long lDataLength = pRs->Fields->GetItem("Image")->ActualSize;
       varBLOB = pRs->GetFields()->GetItem("Image")->GetChunk(lDataLength);
      if(varBLOB.vt == (VT_ARRAY | VT_UI1))       
     {
            BYTE *pBuf = NULL;   
            pBuf = (BYTE*)GlobalAlloc(GMEM_FIXED,lDataLength);
            SafeArrayAccessData(varBLOB.parray,(void **)pBuf); 
            //Build a File in Windows Temp Directory
            char tmpPath[_MAX_PATH+1];
            GetTempPath(_MAX_PATH,tmpPath);
            CString strFileName = "temp.bmp";
            strFileName = tmpPath+strFileName;
                                     
            CFile outFile(strFileName,CFile::modeCreate|CFile::modeWrite);
            LPSTR buffer = (LPSTR)GlobalLock((HGLOBAL)pBuf);
            outFile.WriteHuge(buffer,lDataLength);
            GlobalUnlock((HGLOBAL)pBuf);
            outFile.Close();          
            SafeArrayUnaccessData (varBLOB.parray);
       }

        pRs->Close();
        pConnection->Close();
     }
    catch(_com_error &e)
    {
        // Notify the user of errors if any.
        _bstr_t bstrSource(e.Source());
        _bstr_t bstrDescription(e.Description());
        CString sError;
        sError.Format("Source : %s /n Description : %s/n",(LPCSTR)bstrSource,(LPCSTR)bstrDescription);
        AfxMessageBox(sError);    
 } 

3. VB把文件存入数据库IMAGE字段

Sub savepic(FileName As String, IndexNumber As Long)
   Dim DcnNWind As New ADODB.Connection
   Dim rs As ADODB.Recordset
   Set rs = New ADODB.Recordset
   DcnNWind.CursorLocation = adUseClient
   DcnNWind.Open "Provider=SQLOLEDB.1;Integrated Security=SSPI;Persist Security Info=False;Initial Catalog=CUSTOM;Data Source=SERVER"
   rs.CursorType = adOpenKeyset
   rs.LockType = adLockOptimistic
   rs.Open "CustomInfo", DcnNWind, , adCmdTable
   rs.Move (IndexNumber)
   Call FileToBlob(rs.Fields("Image"), FileName, FileLen(FileName))
   rs.UpdateBatch adAffectCurrent
End Sub

Private Sub FileToBlob(fld As ADODB.Field, FileName As String, Optional ChunkSize As Long )
   Dim fnum As Integer, bytesLeft As Long, bytes As Long
   Dim tmp() As Byte
   If (fld.Attributes And adFldLong) = 0 Then
      Err.Raise 1001, , "Field doesn't support the GetChunk method."
   End If
   fnum = FreeFile
   Open FileName For Binary As fnum
      bytesLeft = LOF(fnum)
   Do While bytesLeft
      bytes = bytesLeft
      If bytes > ChunkSize Then bytes = ChunkSize
      ReDim tmp(1 To bytes) As Byte
      Get #1, , tmp
      fld.AppendChunk tmp
      bytesLeft = bytesLeft - bytes
   Loop
   Close #fnum
End Sub

4. VB把文件从IMAGE字段中读到文件中。

Sub loadpic(IndexNumber As Long)
   Dim DcnNWind As New ADODB.Connection
   Dim rs As ADODB.Recordset
   Set rs = New ADODB.Recordset
   DcnNWind.CursorLocation = adUseClient
   DcnNWind.Open "Provider=SQLOLEDB.1;Integrated Security=SSI;Persist Security Info=False;Initial Catalog=CUSTOM;Data Source=SERVER"
   rs.CursorType = adOpenKeyset
   rs.LockType = adLockOptimistic
   rs.Open "CustomInfo", DcnNWind, , adCmdTable
   rs.Move (IndexNumber)
   Call BlobToFile(rs.Fields("Image"), "c:/windows/temp/tmp.bmp", rs.Fields("Image").ActualSize)
End Sub

Private Sub BlobToFile(fld As ADODB.Field, FileName As String, Optional ChunkSize As Long )
   Dim fnum As Integer, bytesLeft As Long, bytes As Long
   Dim tmp() As Byte
   If (fld.Attributes And adFldLong) = 0 Then
      Err.Raise 1001, , "Field doesn't support the GetChunk method."
   End If
   If Dir$(FileName) <> "" Then Kill FileName
   fnum = FreeFile
   Open FileName For Binary As fnum
   bytesLeft = fld.ActualSize
   Do While bytesLeft
      bytes = bytesLeft
      If bytes > ChunkSize Then bytes = ChunkSize
      tmp = fld.GetChunk(bytes)
      Put #fnum, , tmp
      bytesLeft = bytesLeft - bytes
   Loop
   Close #fnum
End Sub

用VC,VB进行图像数据(二进制大对象)存储数据库的方法

网上经常有人问如何把图像存入数据库中,原先我也是不得要领。经过多方指点和自己在开发过程中的摸索,终于解决这一问题。 下面给出用VC,VB如何操作图像文件存取数据库的原码,帮助一些...
  • neverup_
  • neverup_
  • 2010年06月26日 16:08
  • 651

关于用VC,VB进行图像数据(二进制大对象)存储数据库的一点心得

:网上经常有人问如何把图像存入数据库中,原先我也是不得要领。经过多方指点和自己在开发过程中的摸索,终于解决这一问题。        下面给出用VC,VB如何操作图像文件存取数据库的原码,帮助一些还没有...
  • mynote
  • mynote
  • 2005年02月21日 08:29
  • 1186

关于用VC,VB进行图像数据(二进制大对象)存储数据库的一点心

网上经常有人问如何把图像存入数据库中,原先我也是不得要领。经过多方指点和自己在开发过程中的摸索,终于解决这一问题。       下面给出用VC,VB如何操作图像文件存取数据库的原码,帮助一些还没有掌握...
  • dongliqiang2006
  • dongliqiang2006
  • 2009年03月02日 22:45
  • 385

Halcon vc学习1-图像数据获取、加载

vc添加Halcon库的引用: #include "HalconCpp.h" #pragma  comment(lib,"halconcpp.lib")   //---------------...
  • zcrong
  • zcrong
  • 2012年06月25日 11:32
  • 1466

Oracle数据库对于大对象二进制文件的存储及下载

什么是大对象二进制文件类型?Oracle数据库对于大对象二进制文件的存储可以使用Blob和Clob两种类型字段。 也就是说我们可以向数据库当中直接存储以二进制形式的图片、声音、视频等,此时就需要用到B...
  • daddies999
  • daddies999
  • 2017年07月02日 17:31
  • 415

VB读取本地图片并保存到数据库中

Set mstream = New ADODB.Stream mstream.Type = adTypeBinary mstream.Open m...
  • lsgis2001
  • lsgis2001
  • 2013年07月13日 22:33
  • 1076

VB中调用VC++开发的DLL

转自:http://lanshanlhy.blog.163.com/blog/static/302294762010112832031218/ 再谈在VB中调用VC++开发的DLL  再谈...
  • xl19900502
  • xl19900502
  • 2016年02月22日 11:17
  • 577

谈谈我用Unity5的AssetBundle踩到的几个坑

http://liweizhaolili.lofter.com/post/1cc70144_885b047 谈谈我用Unity5的AssetBundle踩到的几个坑 在上段时间摸索...
  • anypkv
  • anypkv
  • 2017年07月05日 11:13
  • 189

Vb 与 Vc 的区别

一:简单的对比 VB是由Basic语言演化而来的VisualBasic,意思是可视化Basic,而VC是由C++语言演化而来的VisualC++,意思是可视化C++,VB功能没有VC强大,但是很容易...
  • guomutian911
  • guomutian911
  • 2014年10月21日 11:57
  • 2674

关于用存储过程中动态创建视图的一点心得。

工作中遇到的问题,要不然也不会想到要去如何实现了。本来已经创建好了视图,后台的代码也写完了,突然得到指示,其中一张比较重要的表的表名会因为在不同的PC上安装数据库而发生变化(在另一张表中可以根据规则查...
  • vajoy
  • vajoy
  • 2013年01月07日 16:53
  • 4530
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:关于用VC,VB进行图像数据(二进制大对象)存储数据库的一点心得
举报原因:
原因补充:

(最多只允许输入30个字)