COM开发拾粹<二>

原创 2003年04月23日 23:20:00

COM开发拾粹<>

5.自定义错误代码?HRESULT?异常?

COM中的出错处理可以有多种选择,比如用方法的[out,retval]参数返回自定义的错误代码;或返回标准的以及自定义的HRESULT值;抛出异常也是一种选择。采用哪种方法要根据实际情况而定。

返回自定义错误代码是一种源自C语言结构化设计的传统方法,它放弃了C++以及COM的出错处理机制,采用自建的处理方法。代码上少不了要写很多的switch-case语句以捕捉错误代码进行处理。它的缺点是最外层代码要想得到最内层的错误的话,则中间层就必须如实的返回内层的出错代码,这样一层层的抄送给最外层。带来的负作用就是灵活性非常差。

异常(exception)可以解决这个问题。但在COM规范里规定,一个COM组件不能让任何异常逃脱到这个COM之外,原因是你不知道调用这个COM的客户端语言是否支持异常机制,它能不能捕获(catch)到这个异常。规定是死的,人的活的。如果客户端缺定也是C++编写的,并且你也不需要编写那么规范COM,而只要实用就行,那么从COM里抛出异常,客户端来捕获又何妨?不过,这种玩法最好仅在进程内DLL中使用,跨进程、跨机器的异常能不能被正常捕获,COM规范里可没承诺什么,本来你就没用COM的推荐方法嘛。

那什么是COM的推荐方法,答案是HRESULT。我们可以返回一个HRESULT值表示某种错误。很多情况下,我们都懒得去查预定义的HRESULT值,更不愿意自已定义HRESULT了,于是几乎所有的方法都是返回S_OKE_FAIL。其实32位长的HRESULT给我们留出了充足的空间来定义自已的错误码。你可以把HRESULT值定义在IDL文件中,这样当客户端#import这个COM时,也会把定义自动加到*.tlh文件中,无需附加的.h文件声明:

cpp_quote("//自定义错误码")<?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" />

cpp_quote("#define E_IDNOTFOUND 0x8000F001")

cpp_quote("#define E_IDEXIST 0x8000F002")

cpp_quote("#define E_IDREQUIRED 0x8000F003")

客户端处理HRESULT值分为两种情况。如果你用VC写客户端,用#import预编译指令生成了COM的智能封装,那么这个封装会自动把错误的返回码转成一个异常抛出。如下面是#import生成的封装代码:

inline _variant_t IContext::GetContextValue ( _bstr_t PropName ) {

    VARIANT _result;

    VariantInit(&_result);

    HRESULT _hr = get_ContextValue(PropName, &_result); //调用真正的方法

    if (FAILED(_hr)) _com_issue_errorex(_hr, this, __uuidof(this)); //如果返回一个ERROR值,_com_issue_errorex就抛出异常

    return _variant_t(_result, false);

}

这样的封装代码让我们即可以享受到特定语言(C++)提供的便利,又可以在开发COM时遵守统一的规范而不需根据客户端作特殊的处理。

COM组件开发(六)——使用ATL开发COM组件

使用ATL开发COM组件           使用ATL开发COM组件之前,要对几个重要的类进行说明:           CComModule           这是ATL的中心模块类,它的...
  • q5806622
  • q5806622
  • 2015年02月27日 10:10
  • 2231

使用VC6.0开发COM组件 - 傻瓜式,不讲理论,只讲实例

原文地址:http://www.cnblogs.com/lin1270/archive/2013/04/02/2997042.html 1.创建一个ATL COM AppWizard...
  • qq799238350
  • qq799238350
  • 2016年10月08日 16:28
  • 277

COM组件开发(一)—— 对象与接口

一.前言        在COM规范中,最基本的两个要素就是对象与接口,因为COM就是由这两者来共同实现的。COM对象在组件中是被封装起来的,客户代码只能通过接口来访问COM对象并享受其,由于客户与C...
  • q5806622
  • q5806622
  • 2015年01月19日 23:08
  • 3552

COM组件入门(一)

最近需要用到COM组件的知识,看了看COM编程指南,感觉还不错,把我的学习心得记录下来。这是我写...
  • davidsu33
  • davidsu33
  • 2014年08月13日 17:08
  • 1186

C#开发COM组件

原文:http://blog.csdn.net/soudog/article/details/1593346 1.    概述        Microsoft在解决和以往的COM和SDK开发...
  • jiftlixu
  • jiftlixu
  • 2016年03月09日 14:20
  • 3100

C#编写COM组件

C#编写COM组件  软件:Microsoft VisualStudio 2010 1、新建一个类库项目 2、将Class1.cs改为我们想要的名字(例如:MyClass.cs)...
  • kingmax54212008
  • kingmax54212008
  • 2017年06月22日 14:44
  • 2005

activeX com 组件开发 一

com组件开发  可以用vb   c#  vc++  等   个人对c#比较熟练 ,但是c# 做控件弊端太大,要求客户装framework 这比较强人所难 ,当然vb 也要装运行库库 ,vc++可以装...
  • studypower
  • studypower
  • 2014年09月27日 14:06
  • 1380

推荐几款COM组件开发的入门书籍

推荐几本个人读过的比较不错的COM组件相关的书籍,按我的阅读感受排名如下: 1,《Visual C++实践与提高-COM和COM+篇》         这本书我放在第一位,倒不是它有多么出色,但...
  • ghevinn
  • ghevinn
  • 2014年01月25日 17:37
  • 6610

VS2010 简单ATL COM开发(上)

1、打开VS2010,新建ATL COM 项目,步骤:“文件” --》“新建” --》“项目”,选择“Visual C++” --》“ATL 项目” ,填写“名称” FirstCOM --》“确定”。...
  • wangwenjing90
  • wangwenjing90
  • 2013年04月08日 14:03
  • 17735

COM组件开发(三)——类厂对象

COM类厂对象的实现         COM客户程序要使用COM对象是通过COM库创建而来的,而实际上COM库是调用COM对象的类厂来创建的。COM类厂对象也是一个COM对象,所以它也从IUnkno...
  • q5806622
  • q5806622
  • 2015年02月04日 19:32
  • 2414
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:COM开发拾粹<二>
举报原因:
原因补充:

(最多只允许输入30个字)