C技巧:VC訪問數(shù)據(jù)庫技術(shù)的方法實(shí)例

字號(hào):

最常用的數(shù)據(jù)庫訪問技術(shù)有如下幾種
    1.ODBC——開放數(shù)據(jù)庫互聯(lián)
    ODBC為使用不同的關(guān)系數(shù)據(jù)庫提供了一個(gè)統(tǒng)一的程序設(shè)計(jì)接口。在安裝不同的數(shù)據(jù)庫后,需要?jiǎng)?chuàng)建ODBC數(shù)據(jù)源,
    2.DAO——數(shù)據(jù)訪問對(duì)象
    3.RDO——遠(yuǎn)程數(shù)據(jù)對(duì)象
    4.OLE DB——對(duì)象連接與嵌入數(shù)據(jù)庫
    5.ADO——ActiveX數(shù)據(jù)對(duì)象
    這里我說明我使用的兩種方法:ODBC和ADO。
    1.ODBC
    在安裝數(shù)據(jù)庫首先要?jiǎng)?chuàng)建ODBC數(shù)據(jù)源,使用CDatabase和CRecordset兩個(gè)MFC的類與數(shù)據(jù)庫建立連接,訪問數(shù)據(jù)庫。
    1.1條件
    包含頭文件:#include
    聲明成員變量:CDatabase m_dbPostGre;
    1.2連接數(shù)據(jù)庫
    int nRetVal;
    nRetVal = m_dbPostGre.OpenEx( _T( "DSN=PostgreSQL30W;UID=PostGre;PWD=PostGre" ),
    CDatabase::openReadOnly | CDatabase::noOdbcDialog );
    if ( nRetVal )
    {
    AfxMessageBox( _T( "連接數(shù)據(jù)庫成功!" ) );
    }
    1.3訪問數(shù)據(jù)
    CRecordset recordset( &m_dbPostGre );
    CString strSQL = _T( "select * from product" );
    recordset.Open( CRecordset::forwardOnly, strSQL, CRecordset::readOnly );
    CDBVariant var;
    while ( !recordset.IsEOF() )
    {
    TAG_PRODUCTINFO tagProductInfo;
    // ID
    recordset.GetFieldValue( _T( "ID" ), var );
    tagProductInfo.nProductID = var.m_iVal;
    // Name
    recordset.GetFieldValue( _T( "Name" ), tagProductInfo.strProductName );
    m_vecProductInfo.push_back( tagProductInfo );
    recordset.MoveNext();
    }
    recordset.Close();
    2.ADO技術(shù)
    ActiveX Data Object, ActiveX數(shù)據(jù)對(duì)象。
    ADO建立在OLE DB之上,采用ADO技術(shù)訪問數(shù)據(jù)庫的話,實(shí)際的調(diào)用過程是:ADO客戶程序通過ADO再訪問OLE DB提供的程序,這樣訪問速度就要慢一些。
    如果某個(gè)關(guān)系型數(shù)據(jù)庫沒有OLE DB的提供程序,那么可以利用ODBC的OLE DB提供程序去訪問ODBC,然后利用ODBC再去訪問支持ODBC的數(shù)據(jù)庫。
    2.1條件
    l 頭文件和動(dòng)態(tài)庫的加載
    #include
    #include
    #pragma warning(disable:4146)
    #import "C:\Program Files\Common Files\System\ado\msado15.dll" named_guids rename("EOF","adoEOF"), rename("BOF","adoBOF")
    #pragma warning(default:4146)
    using namespace ADODB;
    l COM組件的加載
    if ( CoInitialize( NULL ) != 0 )
    {
    AfxMessageBox( _T( "初始化Com庫失敗!" ) );
    return FALSE;
    }
    l 變量的聲明
    _ConnectionPtr m_pConnection;
    2.2連接數(shù)據(jù)庫
    m_pConnection.CreateInstance( __uuidof(Connection) );
    m_pConnection->ConnectionString = _T( "DSN=PostgreSQL30W;UID=PostGre;PWD=PostGre" );
    HRESULT hr = m_pConnection->Open( _T(""), _T(""), _T(""), adConnectUnspecified );
    if ( SUCCEEDED( hr ) )
    {
    AfxMessageBox( _T( "連接數(shù)據(jù)庫成功!" ) );
    }
    2.3訪問數(shù)據(jù)庫
    _CommandPtr pCommand(__uuidof(Command));
    _RecordsetPtr pRecordset( __uuidof(Recordset) );
    CString strSQL = _T( "select * from \"pg_getProductInfo\"()" );
    try
    {
    pCommand->ActiveConnection=m_pConnection;
    pCommand->CommandText=_bstr_t(strSQL);
    pRecordset=pCommand->Execute(NULL,NULL,adCmdText);
    }
    catch (_com_error & e)
    {
    AfxMessageBox(e.Description());
    return ;
    }
    _variant_t var;
    int nRecordNum = pRecordset->GetRecordCount();
    while( !pRecordset->GetadoEOF() )
    {
    TAG_PRODUCTINFO tagProductInfo;
    // ID
    var = pRecordset->GetCollect( _T( "ID" ) );
    tagProductInfo.nProductID= var.intVal;
    // Name
    var = pRecordset->GetCollect( _T( "Name" ) );
    tagProductInfo.strProductName = (char*)_bstr_t(var);
    m_vecProductInfo.push_back( tagProductInfo );
    pRecordset->MoveNext();
    }
    pRecordset->Close();
    pRecordset.Release();
    總結(jié):
    現(xiàn)在DAO和RDO這兩種技術(shù)已經(jīng)很少使用了,OLE DB和ADO這兩種是比較新的技術(shù),OLE DB的功能非常強(qiáng)大,但是他對(duì)自動(dòng)化的支持不是很好。為了更好地支持自動(dòng)化,微軟在OLE DB的基礎(chǔ)上開發(fā)了ADO,便于像VBScript這樣的腳本語言,以及VB,Delphi這樣的語言都可以很方便的使用ADO去訪問數(shù)據(jù)庫。
    上面兩種技術(shù)對(duì)于不同的關(guān)系數(shù)據(jù)庫,使用方法都是一樣的,不同的就是數(shù)據(jù)源,名稱,密碼以及SQL語句的調(diào)用方式。
    舉個(gè)例子:以調(diào)用存儲(chǔ)過程為例
    SQLServer2000的調(diào)用方法是”{CALL sp_addMember( ’%s’, ’%s’, %d )}”,如果不帶參數(shù),則沒有小括號(hào),如果帶參數(shù),字符串的參數(shù)需要加單引號(hào)。
    PostGre的調(diào)用方法是” _T( "select \"pg_modifyOneProduct\"( %d, ’%s’ )"”,“\“是轉(zhuǎn)義字符,因?yàn)樵赑ostGre定義存儲(chǔ)過程時(shí),如果存儲(chǔ)過程名稱加上了雙引號(hào),那么在調(diào)用的時(shí)候,就一定要加上雙引號(hào),SQL中應(yīng)該就是這么規(guī)定的。還有一個(gè)存儲(chǔ)過程如果是想返回表中所有記錄,那么在調(diào)用存儲(chǔ)過程的時(shí)候就要使用Selece * from 存儲(chǔ)過程名。