求解。。我用的编译器是VC++6.0,建的MFC应用程序对话框模式,使用ado库连接SQL Server2005,请看代码:/************************************/
try
{
HRESULT result=m_pCon->Open("Provider=SQLOLEDB;Persist Security Info=False;Initial
Catalog=INSURANCE;Data Source=我的文档-PC","sa","wh",adModeUnknown);
if (result)
{
AfxMessageBox("连接数据库真的成功啦!");
}
else
{
AfxMessageBox("连接数据库真的失败了!");
}
}
catch(...)
{
AfxMessageBox("连接数据库失败!");
}
/**************************************/我的在SQL Server里建了INSURANCE数据库,也已经建好了表,登陆账号密码都没错,目录下是:
我的文档-PC\数据库\INSURANCE
我的文档-PC即是我的本机名,也是这个服务器名。想问一下是不是我的参数有问题,一直弹出对话框:连接数据库真的失败了!
求解
try
{
HRESULT result=m_pCon->Open("Provider=SQLOLEDB;Persist Security Info=False;Initial
Catalog=INSURANCE;Data Source=我的文档-PC","sa","wh",adModeUnknown);
if (result)
{
AfxMessageBox("连接数据库真的成功啦!");
}
else
{
AfxMessageBox("连接数据库真的失败了!");
}
}
catch(...)
{
AfxMessageBox("连接数据库失败!");
}
/**************************************/我的在SQL Server里建了INSURANCE数据库,也已经建好了表,登陆账号密码都没错,目录下是:
我的文档-PC\数据库\INSURANCE
我的文档-PC即是我的本机名,也是这个服务器名。想问一下是不是我的参数有问题,一直弹出对话框:连接数据库真的失败了!
求解
http://download.microsoft.com/download/4/4/d/44dbde61-b385-4fc2-a67d-48053b8f9fad/sqlncli.msi
代码改这样试下.try
{
HRESULT result=m_pCon->Open("Provider=SQLNCLI;Server=192.168.0.1;Database=myDataBase;Uid=sa; Pwd=sa;","","",adModeUnknown);
if (result)
{
AfxMessageBox("连接数据库真的成功啦!");
}
else
{
AfxMessageBox("连接数据库真的失败了!");
}
}catch(_com_error &e)
{
MessageBox(e.Description(), e.ErrorMessage(), MB_ICONERROR);
}
DataBelong.h#pragma once
struct AddNewCode
{
_variant_t ColName;
_variant_t Value;
};struct FieldInfor
{
_bstr_t Name;
DataTypeEnum Type;
};
//#pragma warning (push)
//以防会产生警告 C4018,但这个警告是没关系的,所以使用下一句代码屏蔽它
//#pragma warning(disable:C4018)
#include "DataBelong.h"
#include <vector>
using namespace std;
class CAdoInterface
{
public:
//获取_ConnectionPtr、_RecordsetPtr
_ConnectionPtr& GetConnPtr() {return m_pCon;}
_RecordsetPtr& GetRecoPtr() {return m_pRec;} //连接某个数据库
void ConnecDataLibrary(LPCTSTR ConnStr,LPCTSTR UserID,
LPCTSTR PassWord,long Options=adModeUnknown);
//关库
void CloseDataLibrary();
//以某种方式打开表单
void OpenSheet(LPCTSTR Sql,
enum CursorTypeEnum CursorType=adOpenDynamic,
enum LockTypeEnum LockType=adLockOptimistic,
long Options=adCmdText);
//关表
void CloseSheet(); //头
BOOL BOF() {return m_pRec->BOF;}
//尾
BOOL adoEOF() {return m_pRec->adoEOF;}
//第一条记录
void MoveFirst() {m_pRec->MoveFirst();}
//最后一条记录
void MoveLast() {m_pRec->MoveLast();}
//向下移动一条记录
void MoveNext() {m_pRec->MoveNext();}
//向上移动一条记录
void MovePrevious() {m_pRec->MovePrevious();}
//移动到指定位置
void Move(long Num) {m_pRec->Move(Num);} //执行SQL语句
_RecordsetPtr Execute(LPCTSTR strSQL, long lOptions = adCmdText); //获取字段内容
BOOL GetCollect(LPCTSTR Name,_variant_t& OutCol);
//---------------------增值操作--------------------------------
//插入一条新的记录
void AddNewRecode(AddNewCode* code,long ColCount);
//删除一条记录
void Delet(enum AffectEnum AffectRecords=adAffectCurrent);
//获取一条记录的容
void GetOneRecord(_variant_t* ColName,long ColCount,
_variant_t* OutValue);
//查找
BOOL Find(LPCTSTR lpszFind,
SearchDirectionEnum SearchDirection = adSearchForward);
//查找下一个
BOOL FindNext();
//排序
BOOL Sort(LPCTSTR lpszSort);
//过滤
BOOL Filter(LPCTSTR lpszFilter); //----------------------扩展包装方法------------------------
//插入一条新的记录
void AddNewRecodeEx(CString ColName, ... );
//读取一条新的记录
void GetOneRecordEx(CString ColName, ... );private:
_ConnectionPtr m_pCon;
_RecordsetPtr m_pRec;
CString m_strFind;
SearchDirectionEnum m_SearchDirection;
//-----------------------算法-----------------------
void Ufo(CString InStr,vector<CString>& OutStr);
void GetNameandType(CString ColName,vector<FieldInfor>& OutVnt);
};
#include "AdoInterface.h"//连接数据库,按参数顺序分别代表连接引擎方式(我采用OLEDB),用户名,密码,选项(同步,异步)默认未知
//注意类型转化LPCTSTR就表示一个指向常固定地址的可以根据一些宏定义改变语义的字符串。LPCTSTR == const TCHAR *
//CString 转LPCTSTR:
//CString cStr;
//const char *lpctStr=(LPCTSTR)cStr;
//LPCTSTR转CString:
//LPCTSTR lpctStr;
//CString cStr=lpctStr;void CAdoInterface::ConnecDataLibrary(LPCTSTR ConnStr,LPCTSTR UserID,
LPCTSTR PassWord,long Options)
{
m_pCon.CreateInstance(__uuidof(Connection)); //实例化m_pCon对象
try
{
HRESULT result=m_pCon->Open(_bstr_t(ConnStr),_bstr_t(UserID),_bstr_t(PassWord),Options); //其他类型转换成_bstr_t可以直接赋值。
//int error=GetLastError();
if (result)
{
AfxMessageBox("连接数据库真的成功啦!");
}
else
{
AfxMessageBox("连接数据库真的失败了!");
}
}
catch(...)
{
AfxMessageBox("连接数据库失败!");
}
}
//关闭数据库连接,直接将m_pCon指针关闭即可
void CAdoInterface::CloseDataLibrary()
{
m_pCon->Close();
}
//以某种方式打开表单;执行SQL语句,游标类型:默认动态游标(能看其它用户对数据所作的增删改)
//锁定类型:乐观锁(逐个)--- 只在调用Update 方法时才锁定记录
//选项默认AdCmdText 指示提供者应按命令的文本定义计算
//乐观的锁策略是把记录必须加锁的时间减到最短,当用户对记录的内容进行编辑时,
//乐观锁不起作用,其他用户可以访问和编辑数据,但当其中的一个用户想要更新数据时,记录就会加上锁;
void CAdoInterface::OpenSheet(LPCTSTR Sql,
enum CursorTypeEnum CursorType,
enum LockTypeEnum LockType, long Options)
{
m_pRec.CreateInstance(__uuidof(Recordset));
try
{
HRESULT result=m_pRec->Open(Sql,m_pCon.GetInterfacePtr(),CursorType,LockType,Options);
if (result)
{
AfxMessageBox("打开表单真的成功啦!");
}
else
{
AfxMessageBox("打开表单失败了!");
}
}
catch(...)
{
AfxMessageBox("打开表单失败!");
}
}
//关表
void CAdoInterface::CloseSheet()
{
try
{
AfxMessageBox("开始关表!");
m_pRec->Close();
AfxMessageBox("关表完毕!");
}
catch(...)
{
AfxMessageBox("关表失败!");
}
}
//执行SQL语句,选项默认AdCmdText 指示提供者应按命令的文本定义计算
_RecordsetPtr CAdoInterface::Execute(LPCTSTR lpszSQL, long lOptions)
{
ASSERT(m_pCon != NULL);
ASSERT(AfxIsValidString(lpszSQL));
try
{
return m_pCon->Execute(_bstr_t(lpszSQL), NULL, lOptions);
}
catch (...)
{
AfxMessageBox("执行SQL语句出错!");
}
return FALSE;
}
//获取字段内容,参数:字段名,输出的字段内容
BOOL CAdoInterface::GetCollect(LPCTSTR Name,_variant_t& OutCol)
{
_variant_t vt;
vt = m_pRec->GetCollect(Name);
if(vt.vt != VT_NULL)
{
OutCol = vt;
return TRUE;
}
else
return FALSE;
}//----------------------增值操作-------------------------------
//code是一个对象可储存两种数据,ColCount表示添加记录条数
void CAdoInterface::AddNewRecode(AddNewCode* code,long ColCount)
{
try
{
m_pRec->AddNew(); //调用函数,添加新纪录
for(int i=0;i<ColCount;++i)
m_pRec->PutCollect(code[i].ColName,code[i].Value); m_pRec->Update(); //调用更新函数
}
catch(...)
{
AfxMessageBox("插入记录不成功!");
}
}
////删除一条记录,默认当前记录
void CAdoInterface::Delet(enum AffectEnum AffectRecords)
{
m_pRec->Delete(AffectRecords);
m_pRec->Update();
}
////获取一条记录的内容,参数:列名,列数量,输出变量
void CAdoInterface::GetOneRecord(_variant_t* ColName,long ColCount,
_variant_t* OutValue)
{
try
{
for(int i=0;i<ColCount;++i)
{
OutValue[i] = m_pRec->GetCollect(ColName[i]);
}
}
catch(...)
{
AfxMessageBox("获取一条记录不成功!");
}
}
//查找,参数字段名
BOOL CAdoInterface::Find(LPCTSTR lpszFind,
SearchDirectionEnum SearchDirection)
{
ASSERT(m_pRec != NULL);
ASSERT(AfxIsValidString(lpszFind));
try
{
if (strcmp(lpszFind, _T("")) != 0)
{
m_strFind = lpszFind;
} if (m_strFind.IsEmpty()) return FALSE;
AfxMessageBox(m_strFind);
HRESULT result=m_pRec->Find(_bstr_t(m_strFind),1, SearchDirection," ");
AfxMessageBox("Find结束!");
if ((adoEOF() || BOF()) )
{
return FALSE;
}
else
{
m_SearchDirection = SearchDirection;
return TRUE;
}
}
catch (...)
{
DWORD a=GetLastError();
AfxMessageBox("Find出错!");
return FALSE;
}
}//查找下一个
BOOL CAdoInterface::FindNext()
{
ASSERT(m_pRec != NULL);
try
{
if (m_strFind.IsEmpty()) return FALSE;
m_pRec->MoveNext();
if ((m_pRec->adoEOF || m_pRec->BOF) )
{
return FALSE;
}
else
{
m_pRec->Find(_bstr_t(m_strFind),0, m_SearchDirection);
if ((m_pRec->adoEOF || m_pRec->BOF) )
{
return FALSE;
}
else
{
return TRUE;
}
}
}
catch (...)
{
AfxMessageBox("FindNext出错!");
return FALSE;
}
}
//排序
BOOL CAdoInterface::Sort(LPCTSTR lpszSort)
{
try
{
m_pRec->PutSort(lpszSort);
return TRUE;
}
catch (...)
{
AfxMessageBox("Sort出错!");
return FALSE;
}
}
//过滤
BOOL CAdoInterface::Filter(LPCTSTR lpszFilter)
{
ASSERT(m_pRec != NULL);
try
{
m_pRec->PutFilter(lpszFilter);
return TRUE;
}
catch (...)
{
AfxMessageBox("Filter出错!");
return FALSE;
}
}//----------------------扩展包装方法--------------------------------
void CAdoInterface::AddNewRecodeEx(CString ColName, ... )
{
//顺序取得字符串ColName中的字段名及字段类型,并将其存入vector中
vector<FieldInfor> vfi;
GetNameandType(ColName,vfi);
//将指定字符串ColName后面的省略号处的所有参数按顺序存入void*数组中
vector<void*> vpn;
void* pp = (&ColName) + (sizeof(ColName)/sizeof(CString));
vpn.push_back(pp);
for(int i=1;i<vfi.size();++i)
{
if(vfi[i-1].Type == 4 || vfi[i-1].Type == 5)
{
void* pp = (double*)vpn[i-1] +
(sizeof(*(double*)vpn[i-1])/sizeof(double));
vpn.push_back(pp);
}
else
{
void* pp = (CString*)vpn[i-1] +
(sizeof(*(CString*)vpn[i-1])/sizeof(CString));
vpn.push_back(pp);
}
}
//写数据
m_pRec->AddNew();
for(int m=0;m<vfi.size();m++)
{
if(vfi[m].Type == 2
|| vfi[m].Type == 3
|| vfi[m].Type == 16
|| vfi[m].Type == 17
|| vfi[m].Type == 18
|| vfi[m].Type == 19
|| vfi[m].Type == 20
|| vfi[m].Type == 21)
{
m_pRec->PutCollect(vfi[m].Name , _variant_t(*(long*)vpn[m]));
}
else if(vfi[m].Type == 4 || vfi[m].Type == 5)
{
m_pRec->PutCollect(vfi[m].Name , _variant_t(*(double*)vpn[m]));
}
else
{
m_pRec->PutCollect(vfi[m].Name , _variant_t(*(CString*)vpn[m]));
}
}
m_pRec->Update();
}void CAdoInterface::GetOneRecordEx(CString ColName, ... )
{
//顺序取得字符串ColName中的字段名及字段类型,并将其存入vector中
vector<FieldInfor> vfi;
GetNameandType(ColName,vfi);
//将指定字符串ColName后面的省略号处的所有参数按顺序存入void**数组中
vector<void**> vpn;
void** pp = (void**)((&ColName) + (sizeof(ColName)/sizeof(CString)));
vpn.push_back(pp);
for(int k=1;k<vfi.size();++k)
{
void** pp = vpn[k-1] + 1;
vpn.push_back(pp);
} //获取字段数据,并按字段名类型向外传出值
for(int i=0;i<vfi.size();++i)
{
_variant_t var;
var = m_pRec->GetCollect(vfi[i].Name);
if(var.vt != VT_NULL)
{
if(vfi[i].Type == 2
|| vfi[i].Type == 3
|| vfi[i].Type == 16
|| vfi[i].Type == 17
|| vfi[i].Type == 18
|| vfi[i].Type == 19
|| vfi[i].Type == 20
|| vfi[i].Type == 21)
{
*((long*)(*vpn[i])) = var;
}
else if(vfi[i].Type == 4 || vfi[i].Type == 5)
{
*((double*)(*vpn[i])) = var;
}
else
{
*((CString*)(*vpn[i])) = (LPCSTR)_bstr_t(var);
}
}
}
}//---------------------------算法--------------------------------
void CAdoInterface::Ufo(CString InStr,vector<CString>& OutStr)
{
vector<char> bug;
vector<CString> newbug;
vector<CString> result;
for(int j=0;j<InStr.GetLength();++j)
{
if(InStr[j] != ',')
bug.push_back(InStr[j]);
else
{
CString sa;
for(int i=0;i<bug.size();++i)
{
sa += bug[i];
}
result.push_back(sa);
bug.clear();
}
}
CString sa;
for(int i=0;i<bug.size();++i)
{
sa += bug[i];
}
result.push_back(sa);
OutStr = result;
}void CAdoInterface::GetNameandType(CString ColName,vector<FieldInfor>& OutVnt)
{
//将指定字符串ColName中的字段名按顺序萃取到数组中,并且获取相应
//字段的类型信息,该算法需要依赖一个Name与Type的结构才能完成
//1、取出某表所有字段名及字段类型
FieldPtr fp;
vector<FieldInfor> vfi;
int Count = m_pRec->Fields->GetCount();
for(int i=0;i<Count;++i)
{
FieldInfor fi;
fp = m_pRec->Fields->GetItem(long(i));
fi.Name = fp->Name;
fi.Type = fp->Type;
vfi.push_back(fi);
}
//2、将指定字符串ColName中的字段名按顺序萃取到数组中
vector<CString> vColName;
Ufo(ColName,vColName);
//3、从全部字段名中找出与字符串ColName中字段名相符的字段,并连同
//该字段的类型一同存入出参的OutVnt中
for(int n=0;i<vColName.size();++n)
{
for(int j=0;j<vfi.size();++j)
{
if(vColName[n] == (LPCTSTR)vfi[j].Name)
{
OutVnt.push_back(vfi[j]);
}
}
}
}