ADO+MFC数据库编程常用语句

设在OnInitDialog()函数中,已经完成了初始化COM,创建ADO连接等操作,即

// 初始化COM,创建ADO连接等操作
	if (!AfxOleInit()) {
		AfxMessageBox("OLE/COM初始化失败");
		return FALSE;
}
    HRESULT hr;
	try
	{
	//	hr = m_pConnection.CreateInstance("ADODB.Connection");///创建Connection对象
		hr = 	m_pConnection.CreateInstance(__uuidof(Connection));
		if(SUCCEEDED(hr))
		{
			hr = m_pConnection->Open("Provider=Microsoft.Jet.OLEDB.4.0;Data Source=test1.mdb","","",adModeUnknown);///连接

		//	hr = m_pConnection->Open("Provider=SQLOLEDB;server=(local);UID=sa;PWD=123;database=test1","","",adModeUnknown);

		}
	}
	catch(_com_error e)///捕捉异常
	{
		CString errormessage;
		errormessage.Format("连接数据库失败!\r错误信息:%s",e.ErrorMessage());
		AfxMessageBox(errormessage);///显示错误信息
    }



一、点击”读取按钮“,从数据库中读取数据,在界面上显示,有三种方法:

void CMyLinkMdbDlg::OnReadAccess() 
{
	// TODO: Add your control notification handler code here
  /*******************以下提供了3种形式方法执行SQL命令*****************/

	/*  ***********第一种  用Execute 执行SQL命令**********   

 	try
  	{
	m_pRecordset.CreateInstance("ADODB.Recordset");
	_bstr_t strCmd="SELECT * FROM [user]";
 	m_pRecordset=m_pConnection->Execute(strCmd,&RecordsAffected,adCmdText);
 	}
  	catch(_com_error *e)
 	{
  		AfxMessageBox(e->Description());
  	}
 */


	 /************第二种   用command命令操作SQL语句************
	 	m_pCommand.CreateInstance("ADODB.Command");
	 	_variant_t vNULL;
	 	vNULL.vt = VT_ERROR;
	 	vNULL.scode = DISP_E_PARAMNOTFOUND;///定义为无参数
	 	m_pCommand->ActiveConnection = m_pConnection;///非常关键的一句,将建立的连接赋值给它
	 	m_pCommand->CommandText = "SELECT * FROM [user]";///命令字串
    	m_pRecordset = m_pCommand->Execute(&vNULL,&vNULL,adCmdText);///执行命令,取得记录集
     */

   /**************第三种   直接用open执行SQL语句 *************/
    m_pRecordset.CreateInstance(__uuidof(Recordset));
	try
	{
		m_pRecordset->CursorLocation   =   adUseClient;          //若需要排序的话必须要
		m_pRecordset->Open("SELECT * FROM [user1]",                // 查询DemoTable表中所有字段
			_variant_t((IDispatch *)m_pConnection,true),	 // 获取库接库的IDispatch指针
			adOpenDynamic,
			adLockOptimistic,
			adCmdText);
		m_pRecordset->Sort   =   "id   asc";          //按照id升序排序

	}
	catch(_com_error *e)
	{
		AfxMessageBox(e->ErrorMessage());
	}
  




	_variant_t vID,vName,vAge;          
	// 清空列表框
	m_DataList.ResetContent();
	m_DataList.SetCurSel(0);
	vName=vAge="";
	// 在ADO操作中建议语句中要常用try...catch()来捕获错误信息,
	// 因为它有时会经常出现一些想不到的错误。jingzhou xu

	try
	{
		if(!m_pRecordset->BOF)
			m_pRecordset->MoveFirst();
		else
		{
			AfxMessageBox("表内数据为空");
			return;
		}
        	CString strtemp;
			while (!m_pRecordset->adoEOF)
			{
			    strtemp = "";
				vID=m_pRecordset->GetCollect(_variant_t((long)0));
				//取得第1列的值,从0开始计数,你也可以直接列出列的名称,如下一行
				vName=m_pRecordset->GetCollect("name");
				vAge=m_pRecordset->GetCollect("age");
				
			
				if(vID.vt != VT_NULL)
				{
					strtemp.Format("%d",vID.lVal);
				}
				
				if(vName.vt != VT_NULL)
				{
					strtemp += "             ";
					strtemp += (LPCTSTR)(_bstr_t)vName;
				}
				
				if(vAge.vt != VT_NULL)
				{
					strtemp += "             ";
					strtemp += (LPCTSTR)(_bstr_t)vAge;
				}			
				m_DataList.AddString(strtemp);	
				UpdateData(FALSE);		
				m_pRecordset->MoveNext();
			}
			m_DataList.SetCurSel(0);
            OnSelchangeData();
		
	}
	catch(_com_error *e)
	{
		AfxMessageBox(e->ErrorMessage());
	}
	m_pRecordset->Close();
	m_pRecordset=NULL;

}


二、插入数据

void CMyLinkMdbDlg::OnInsert() 
{
	// TODO: Add your control notification handler code here
	UpdateData(TRUE);
	if (m_Age == "" || m_Name == "")
	{
		AfxMessageBox("输入不能为空");
		return;
	}

    m_pRecordset.CreateInstance(__uuidof(Recordset));
	try
	{
		m_pRecordset->Open("SELECT * FROM [user1]",                // 查询DemoTable表中所有字段
			_variant_t((IDispatch *)m_pConnection,true),	 // 获取库接库的IDispatch指针
			adOpenDynamic,
			adLockOptimistic,
			adCmdText);
		m_pRecordset->AddNew();                         //用这种方法添加数据就必须用open 语句执行SQL语句
		m_pRecordset->PutCollect("name", _variant_t(m_Name));
		m_pRecordset->PutCollect("age", atol(m_Age));
		m_pRecordset->Update();
     	m_pRecordset->Close();
		AfxMessageBox("插入成功!");
		OnReadAccess();

	}
	catch(_com_error *e)
	{
		AfxMessageBox(e->ErrorMessage());
  	}

	m_pRecordset=NULL;

}

三、修改数据

void CMyLinkMdbDlg::OnModify() 
{
	// TODO: Add your control notification handler code here
	int cursel = m_DataList.GetCurSel();         //得到当前所选记录的索引

	UpdateData(TRUE);
	if (m_Age == "" || m_Name == "")
	{
		AfxMessageBox("输入不能为空");
		return;
	}
    m_pRecordset.CreateInstance(__uuidof(Recordset));
	try
	{
		m_pRecordset->Open("SELECT * FROM [user1]",                // 查询DemoTable表中所有字段
			_variant_t((IDispatch *)m_pConnection,true),	 // 获取库接库的IDispatch指针
			adOpenDynamic,
			adLockOptimistic,
			adCmdText);
		m_pRecordset->MoveFirst();
		m_pRecordset->Move(cursel);
		m_pRecordset->PutCollect("name", _variant_t(m_Name));
		m_pRecordset->PutCollect("age", atol(m_Age));
		m_pRecordset->Update();
		m_pRecordset->Close();
		OnReadAccess();                 //修改后需重新读取数据库

		m_DataList.SetCurSel(cursel);       //修改后指针仍旧指向刚修改的记录
		
	}
	catch(_com_error *e)
	{
		AfxMessageBox(e->ErrorMessage());
	}
	
	m_pRecordset=NULL;
}

四、删除数据

void CMyLinkMdbDlg::OnDelete() 
{
	// TODO: Add your control notification handler code here
	int cursel = m_DataList.GetCurSel();         //得到当前所选记录的索引
	
    m_pRecordset.CreateInstance(__uuidof(Recordset));
	try
	{
		m_pRecordset->Open("SELECT * FROM [user1]",                // 查询DemoTable表中所有字段
			_variant_t((IDispatch *)m_pConnection,true),	 // 获取库接库的IDispatch指针
			adOpenDynamic,
			adLockOptimistic,
			adCmdText);
		m_pRecordset->MoveFirst();
		m_pRecordset->Move(cursel);
		m_pRecordset->Delete(adAffectCurrent);             //参数adAffectCurrent为删除当前记录
		m_pRecordset->Update();
		m_pRecordset->Close();
		OnReadAccess();                 //修改后需重新读取数据库
		
		m_DataList.SetCurSel(cursel - 1);
		
	}
	catch(_com_error *e)
	{
		AfxMessageBox(e->ErrorMessage());
	}
	
	m_pRecordset=NULL;
}


以上四部分完成了数据库最常用的增、删、改、查功能~

先在程序初始化函数中完成COM的初始化和数据库的连接,再在每一个增删改查的函数中,创建记录集

m_pRecordset
用m_pRecordset调用Open函数,打开数据库,获取数据记录集,

再用m_pRecordset就可以灵活调用数据库了~~



在读取数据库内容函数中:

(1)

if(!m_pRecordset->BOF)
m_pRecordset->MoveFirst();

还有

while (!m_pRecordset->adoEOF)

{

……

m_pRecordset->MoveNext();

……

}


这里就涉及到BOF和EOF的作用,其实上面的 if 和 while 的写法基本上就是固定的了,在不同的应用程序里都差不多~~

简单的说,

~使用 BOF 和 EOF(adoEOF) 属性可确定 Recordset 对象是否包含记录,或者从一个记录移动到另一个记录时是否超出 Recordset 对象的限制。
~如果当前记录位于第一个记录之前,BOF 属性将返回 True (-1),如果当前记录为第一个记录或位于其后则将返回 False (0)。 
~如果当前记录位于 Recordset 对象的最后一个记录之后 EOF(adoEOF)  属性将返回 True,而当前记录为 Recordset 对象的最后一个记录或位于其前,则将返回 False。
~如果 BOF 或 EOF (adoEOF) 属性为 True,则没有当前记录

也即是说,if(!m_pRecordset->BOF)
m_pRecordset->MoveFirst();

这里的作用就是,如果表内数据不为空,就把记录集指针移动到第一条记录(MoveFirst),移动指针到记录集中的第一行)

现在就可以用m_pRecordset调用其他函数对数据库里的内容进行操作了~~


在while循环中,易看出,当我们读取记录集中的数据时,只要没有读到末尾,那么,一直调用m_pRecordset->MoveNext(); 让指针下移~~


(2)在”插入数据库“部分,有以下代码:

m_pRecordset->AddNew();                         //用这种方法添加数据就必须用open 语句执行SQL语句
m_pRecordset->PutCollect("name", _variant_t(m_Name));
m_pRecordset->PutCollect("age", atol(m_Age));
m_pRecordset->Update();
      m_pRecordset->Close();

AddNew 这个是让表添加一个新行
再执行下面两个Putcollect ,
put 放入的意思。这里是把m_Name值放入表中的name字段中;m_Age放入age 字段中~~
Update是更新数据记录集
Close是关闭数据记录集~
 
(3)在”修改数据“部分,有下列代码:
		m_pRecordset->MoveFirst();
 m_pRecordset->Move(cursel);
 m_pRecordset->PutCollect("name", _variant_t(m_Name));
 m_pRecordset->PutCollect("age", atol(m_Age));
 m_pRecordset->Update();
 m_pRecordset->Close();
MoveFirst 移动指针到记录集的第一行(即,设置默认情况下,指针在第一行)
Move(cursel),移动到cursel行,即移动到光标指向的位置 (光标的位置要响应ListBox的单击响应函数)
由于记录集指针在光标指向的位置,所以再执行下面两个PutCollect 函数时,再往该行中写入数据,相当于把原来该行的数据覆盖了~~就能起到修改的作用~~




 

你可能感兴趣的:(ADO+MFC数据库编程常用语句)