在VC++ 6.0 环境下,直接用C(没用MFC)写了一个数据库访问程序。问题: 1 利用Recordset对象读取数据库中的字符串字段时,如何将通过GetCollect()得到的_variant_t类型(GetCollect()的返回值)转换为字符串(string或char*)? 2 在我的程序里,访问数据库的用户有INSERT,UPDATE,DELETE,SELECT等所有权限,但不能对表执行Add和Delete操作。Recordset的AddNew()和Delete()使用还有其它什么限制吗?如何Add和Delete呢? #import "...\msado15.dll" _ConnectionPtr pConnection;
_RecordsetPtr pRecordset; HRESULT hr; if(FAILED(::CoInitialize(NULL)))
return -1; try
{
hr = pConnection.CreateInstance("ADODB.Connection");
pRecordset.CreateInstance( _uuidof(Recordset) ); if(SUCCEEDED(hr))
{
_bstr_t connStr( "..." );
hr = pConnection->Open( connStr,... );
pRecordset->Open( ....); pRecordset->MoveFirst(); // 调试时此句会出错。此时 _com_error 对象 e 的 __vfptr 为:
// 0x004353d0 const _com_error::'vftable'
// command 窗口出现的错误提示为:
// error : Unknown error 0x800A0CB3
pRecordset->Delete(adAffectCurrent); for( int i = 0; i < 2; ++i )
{
// 调试时,能够在Watch窗口正确显示出 var1, var2 里面的 // 字符串信息。我的问题是:如何把它里面的字符串提出来
_variant_t var1 = pRecordset->GetCollect("aaa");
_variant_t var2 = pRecordset->GetCollect("bbb"); // 调试时此句会出错,错误同调用Delete时一样
pRecordset->AddNew();
pRecordset->PutCollect( "aaa", _variant_t("BX3Y2Z1") );
pRecordset->PutCollect( "bbb", _variant_t("HWI9214") );
}
pRecordset->Update(); pRecordset->Close();
pConnection->Close();
}
}
catch(_com_error e)
{
cout << "error : " << e.ErrorMessage() << endl;
} ::CoUninitialize();把 _variant_t 变量var1,var2 用Detatch()方法得到 VARIANT 变量结构体后,里面有一个类型为 char FAR* 的 pcVal 变量,直接输出该变量时只能得到两个字段里面的第一个字符(与表里对照,这是正确的)。
_RecordsetPtr pRecordset; HRESULT hr; if(FAILED(::CoInitialize(NULL)))
return -1; try
{
hr = pConnection.CreateInstance("ADODB.Connection");
pRecordset.CreateInstance( _uuidof(Recordset) ); if(SUCCEEDED(hr))
{
_bstr_t connStr( "..." );
hr = pConnection->Open( connStr,... );
pRecordset->Open( ....); pRecordset->MoveFirst(); // 调试时此句会出错。此时 _com_error 对象 e 的 __vfptr 为:
// 0x004353d0 const _com_error::'vftable'
// command 窗口出现的错误提示为:
// error : Unknown error 0x800A0CB3
pRecordset->Delete(adAffectCurrent); for( int i = 0; i < 2; ++i )
{
// 调试时,能够在Watch窗口正确显示出 var1, var2 里面的 // 字符串信息。我的问题是:如何把它里面的字符串提出来
_variant_t var1 = pRecordset->GetCollect("aaa");
_variant_t var2 = pRecordset->GetCollect("bbb"); // 调试时此句会出错,错误同调用Delete时一样
pRecordset->AddNew();
pRecordset->PutCollect( "aaa", _variant_t("BX3Y2Z1") );
pRecordset->PutCollect( "bbb", _variant_t("HWI9214") );
}
pRecordset->Update(); pRecordset->Close();
pConnection->Close();
}
}
catch(_com_error e)
{
cout << "error : " << e.ErrorMessage() << endl;
} ::CoUninitialize();把 _variant_t 变量var1,var2 用Detatch()方法得到 VARIANT 变量结构体后,里面有一个类型为 char FAR* 的 pcVal 变量,直接输出该变量时只能得到两个字段里面的第一个字符(与表里对照,这是正确的)。
之前判断pRecordset->BOF
还要看你的打开方式是否允许插入和删除?
在MFC下,到Delete句时的错误为:Unknown error 0x800A0CB3;注掉Delete句,到AddNew句后错误一样。
ADO出错时的提示信息:IDispatch error #xxxx 在什么地方(MSDN?书籍?杂志?)可以找到?3x!
pRecordset->Open("select * from boxInfo", connStr, adOpenDynamic, adLockOptimistic, adCmdText );第三个和第四个参数表明,我可以对进行增删操作。此时,try 段内的 for 循环能够执行一次,第二次 AddNew 时就会出错:{DB_E_INTEGRITYVIOLATION} IDispatch error #3119不符合数据库的完整性约束。关于 Open 方法的第四个参数即 LockType,当其为 adLockOptimistic 时,MSDN说:Indicates optimistic locking, record by record. The provider uses optimistic locking, locking records only when you call the Update method.这里的所谓"lock"应当是指当我作出什么操作时,会"lock"住其它用户(线程)对该表(记录)的操作吧,而不是"lock"我自己对表的操作。也就是说,如果用 adLockOptimistic 的话,只有当我 Update 的时候,才会对表执行"lock"动作。
我也不知道在哪儿看的?VC 有个LookUp工具可以查看一些错误的