我在主线程APP的InitInstance函数中初始化组件库
HRESULT hr = CoInitialize(NULL);
if (FAILED(hr))
{
return FALSE;
}
在随后的操作中创建子线程用于操作数据库
CWinThread *pThread = NULL;
pThread = AfxBeginThread(
OperateDatabase,
(LPVOID) this,
THREAD_PRIORITY_NORMAL,
0,
CREATE_SUSPENDED,
NULL);
if (pThread != NULL)
{
ResetEvent(g_hStopEvent);
pThread->ResumeThread();
}
在子线程中,我创建ADO的_ConnectionPtr连接对象
ado27::_ConnectionPtr pCnct = NULL;
hr = pCnct.CreateInstance(__uuidof(ado27::Connection));
if (FAILED(hr))
{
LPVOID lpMsgBuf;
FormatMessage(
FORMAT_MESSAGE_FROM_SYSTEM
                          | FORMAT_MESSAGE_ALLOCATE_BUFFER,
NULL,
(DWORD) hr,
0,
(LPTSTR) &lpMsgBuf,
0,
NULL);                  MessageBox(
                        NULL, 
                        (LPTSTR) lpMsgBuf,
                        "数据库连接错误",
                        MB_OK | MB_ICONERROR); LocalFree(lpMsgBuf); }但是CreateInstance总是报错: 0x0013e350 "标记没有引用存储"。
如果我在子线程中初始化组件库的话,CreateInstance将会正确执行,但是这个线程会被多次调用,在这里初始化组件库效率会太低,不知道有没有别的好方法。

解决方案 »

  1.   

    有没有在执行前调用ADO的LIB文件!
      

  2.   

    我只是在StdAfx.h头文件中加入以下代码#pragma warning(disable: 4146)
    #import "C:\Program Files\Common Files\System\ADO\msado15.dll" rename_namespace("ado27") rename("EOF", "adoEOF")
    #pragma warning(default: 4146)
      

  3.   

    _ConnectionPtr pConn("ADODB.Connection");
    _RecordsetPtr  pRst("ADODB.Recordset");

    pConn->Open(m_sAdoConnString, "", "", adConnectUnspecified); // adAsyncConnect
    我在线程里这样用是没问题的,你可以试试
      

  4.   

    robothn(雷鸟):
    我用你说的方法试了一遍,可是出现一奇怪的问题。第一次调试的时候没有问题,
    但是在随后的调试中,却出现同样的错误("标记没有引用存储"),这是怎么一回事?
      

  5.   

    应该没有问题,我的一个刚刚结束的项目就在多线程中用到ADO.并且是在dll中用的。现在这个项目已经交付客户了。/^&&^\
      -- 
      

  6.   

    我的从没有出过这种问题,可能你Ado环境有问题??"Provider=sqloledb;Data Source=192.168.0.141;Initial Catalog=call;User Id=aaa;Password=;"
    这是我的连接串// stdafx.h
    #import "c:\Program Files\Common Files\System\ADO\msado15.dll" no_namespace rename("EOF", "EndOfFile")
      

  7.   

    要在线程里,初始化COM环境,或在app的 初始化化函数里,初始化多线程的 
    com 环境。
      

  8.   

    在线程开始用::CoInitialize(NULL);
    结束用 ::CoUninitialize();
      

  9.   

    必须在线程中使用CoInitialize();和CoUninitialize();原因和COM库的线程模型有关,MSDN上有比较详细的说明。
      

  10.   

    因为adodb中的对象是套间线程的,必须在创建对象的线程中初始化com库
      

  11.   

    CoInitializeEx创建的对象接口才可以用于多线程
    参见http://expert.csdn.net/Expert/FAQ/FAQ_Index.asp?id=84