我是一些使用智能COM指针迭代MS Outlook联系人的ATL代码,而在某些PC上,我收到每个联系人的COM错误0x80004003(“无效指针”)。相同的代码在其他PC上运行良好。代码如下所示:
_ApplicationPtr ptr;
ptr.CreateInstance(CLSID_Application);
_NameSpacePtr ns = ptr->GetNamespace(_T("MAPI"));
MAPIFolderPtr folder = ns->GetDefaultFolder(olFolderContacts);
_ItemsPtr items = folder->Items;
const long count = items->GetCount();
for (long i = 1; i <= count; i++)
{
try
{
_ContactItemPtr contactitem = items->Item(i);
// The following line throws a 0x80004003 exception on some machines
ATLTRACE(_T("\tContact name: %s\n"), static_cast<LPCTSTR>(contactitem->FullName));
}
catch (const _com_error& e)
{
ATLTRACE(_T("%s\n"), e.ErrorMessage());
}
}
我想知道是否有任何其他应用程序/加载项可能导致此问题?欢迎任何帮助。
答案 0 :(得分:1)
FullName是一个属性,你执行GET操作(它在IDL中可能是这样的:get_FullName([out,retval] BSTR * o_sResult))。这样的操作可以使用空值。
我的假设是contactItem
智能指针指向任何有效的COM对象。在这种情况下,ATLTRACE
完成的格式化操作可能会导致问题。在内部,它的行为可能与标准sprintf("",args...)
函数相似。
为避免此类问题,请执行以下操作:
ATLTRACE(_T("\tContact name: %s\n"),
_bstr_t(contactitem->FullName)?static_cast<LPCTSTR>(contactitem->FullName):"(Empty)")
答案 1 :(得分:0)
猜猜: 也许地址簿中的“FullName”字段为空,这就是指针无效的原因?
很难说,因为您的代码并未指出您正在使用哪些COM接口。
答案 2 :(得分:0)
这会有什么不同吗?
ATLTRACE(_T("\tContact name: %s\n"), static_cast<LPCTSTR>(contactitem->GetFullName()));
答案 3 :(得分:0)
在我的示例中,您将NULL值格式化为正确的文本值。
如果问题是关于FullName(作为属性)和GetFullName()(作为方法)之间的区别,那么答案是否定的。属性和方法应该给出相同的结果。有时属性可以映射到不同的方法,然后是setXXX和getXXX。它可以通过在IDL中使用某些特定语法来实现(实际上在将IDL编译为TLB之后在TLB中实现)。如果属性FullName未映射到方法GetFullName,那么您将获得不同的结果。
因此,请在将某个类型库导入项目后检查文件* .tlh ...