再看ODBC数据访问

来源:互联网 发布:linux网站管理系统限速 编辑:程序博客网 时间:2024/06/05 16:25

以前用过ODBC忘了不少,准备学着开始用ADO了。

ODBC有几种访问数据库的方式。

首先要创建好数据库,然后注册数据源。注册数据源可以用API函数实现。

一个CDatabase对象对应一个数据库。一般可以设置为全局的,在程序初始化时打开,在程序结束前关闭。

CDatabase g_db;

g_db.Open(...);

接下来使用CRecordset类,有两种方式:

1.在需要访问的地方定义临时变量,CRecordset set(&g_db);

查询时:CString strSQL;

            strSQL.Format(_T("select * from info_table where id = %s"),m_id);

            set.Open(CRecordset::forwardonly,strSQL);

            while(!set.ISEOF())

            {

                           ........

                          set.MoveNext();

             }

执行更新,插入操作时可以:g_db.ExecuteSQL(strSQL);strSQL里是相应的SQL语句了

2.上述方法灵活但是不清晰,另一种通常的做法是针对每一个表建立一个类派生自CRecordset:

如:

//////////////////////////////////////////RstClass.h

class CRstClass : public CRecordset
{
public:
 CRstClass(CDatabase* pDatabase = NULL);
 DECLARE_DYNAMIC(CRstClass)

// Field/Param Data
 //{{AFX_FIELD(CRstClass, CRecordset)
 long m_F_ID;
 CString m_F_AutoNo;
 CString m_F_Teacher;
 CTime m_F_Date;
 long m_F_Noon;
 CString m_F_Remark;
 //}}AFX_FIELD


// Overrides
 // ClassWizard generated virtual function overrides
 //{{AFX_VIRTUAL(CRstClass)
 public:
 virtual CString GetDefaultConnect();    // Default connection string
 virtual CString GetDefaultSQL();    // Default SQL for Recordset
 virtual void DoFieldExchange(CFieldExchange* pFX);  // RFX support
 //}}AFX_VIRTUAL

// Implementation
#ifdef _DEBUG
 virtual void AssertValid() const;
 virtual void Dump(CDumpContext& dc) const;
#endif
};
///////////////////////////////////////////////RstClass.cpp

CString CRstClass::GetDefaultConnect()
{
 return _T("ODBC;DSN=Auto");
}

CString CRstClass::GetDefaultSQL()
{
 return _T("[T_Class]");
}

void CRstClass::DoFieldExchange(CFieldExchange* pFX)
{
 //{{AFX_FIELD_MAP(CRstClass)
 pFX->SetFieldType(CFieldExchange::outputColumn);
 RFX_Long(pFX, _T("[F_ID]"), m_F_ID);
 RFX_Text(pFX, _T("[F_AutoNo]"), m_F_AutoNo);
 RFX_Text(pFX, _T("[F_Teacher]"), m_F_Teacher);
 RFX_Date(pFX, _T("[F_Date]"), m_F_Date);
 RFX_Long(pFX, _T("[F_Noon]"), m_F_Noon);
 RFX_Text(pFX, _T("[F_Remark]"), m_F_Remark);
 //}}AFX_FIELD_MAP
}

当用向导生成CRecordset的派生类是会有一个选择框让你选择一个表,然后会将表中的字段与类的成员变量进行绑定。

这样以后一切都变得清晰了:

当要操作一个表如:info_table

对应的CRecordset派生类为:CSetInfo_table;

针对没条记录再见一个类:Cinfo_tableObj;

首先定义一个对象CSetInfo_table set(&g_db);//也可以在CSetinfo_table的构造函数中指定m_pDatabase为 &g_db,这里就不需要参数了,如果都没有指定,则调用GetDefaultConnect()函数获取,也就是说当我们指定了,GetDefaultConnect()函数将不会被调用

查询:其实有两种方式,第一种同上,第二种是给m_strFilter成员变量赋值然后set.Open()就可以了

然后while(!set.IsEOF())

{

       Cinfo_tableObj *pObj = new Cinfo_tableObj();

       pObj->FillBySet(set);

       m_array.add(pObj);

}

添加新记录

set.m_strFilter.Format("F_TableName='%s'",sTableName);

set.Open();

set.AddNew();

pObj->FillToSet(set);

set.Update();

更新新纪录

set.m_strFilter.Format(_T("...."));

set.Open();

set.Edit();

set.FillToSet(set);

set.Update();

 

用户DSN只在本机上用,系统DSN可以在整个网络上用

 

可以利用已有的数据源如 MS Access Database;

数据库连接的时候指定一个数据库就行了,如:

strCon.Format("DSN=MS Access Database;DBQ=%s;DefaultDir=%s;DriverId=281;FIL=MS Access;MaxBufferSize=2048;PageTimeout=5;UID=admin;",
     m_sDBN,
     m_sAppPath);

m_db.OpenEx(strCon,CDatabase::noOdbcDialog);

 

暂且到这里