Request对象内幕--如何通过IDispatch接口返回BSTR字符串

在ASP开发中,我们经常会用到类似这样的调用 oUserName=Request("UserName")。可以肯定的是,我们需要得到的是一个字符串值,事实上,我们也把oUserName作为一个字符值来使用。
作为一个完整的调用应该是这样的:oUserName=CStr(Request.Item("UserName"))

接下来我们看,Request对象是如何通过COM自动化技术来支持形如Request("UserName")的调用的。

通过查看类型库,知道Request对象派生自接口IRequest,IRequest提供如下只读属性的申明。

[id(00000000), propget]
HRESULT Item(
                [in] BSTR bstrVar,
                [out, retval] IDispatch** ppObjReturn);

只读属性Item的DISPID为0,说明它是一个缺省属性,通过脚本调用时,不必显式写出。该属性的传入参数是一个字符串,传出值是一个IDispatch*接口指针。原来,上面得到的oUserName其实是一个IDispatch接口,并不是字符串值,只是在后面的调用中会自动实现IDispatch接口到字符串的转换,从而在表面上我们可以直接把它作为一个字符串来看待。

下面的问题是,IDispatch接口怎么就会自动转换。在自动化编程中,对于各种自动化类型之间的转换主要通过VariantChangeTypeVariantChangeTypeEx进行。

下面是函数VariantChangeTypeEx的声明
HRESULT VariantChangeTypeEx(
  VARIANTARG * pvargDest, 
  VARIANTARG * pvarSrc, 
  LCID  lcid,            
  unsigned short wFlags, 
  VARTYPE vt             
);

MSDN中对函数有这么一段解释。
An object is coerced to a value by invoking the object's Value property (DISPID_VALUE).
翻译过来是,通过调用对象的Value属性(属性ID为DISPID_VALUE),将此对象强制转换为一个值。
其中DISPID_VALUE就是0,VariantChangeType在进行转换时,如果发现pvarSrc是一个IDispatch接口,就会自动调用DISPID为0的属性方法,从而由这个属性方法来具体实现IDispatch接口到其他值的转换。

IDispatch接口具体转换成什么类型的值,由DISPID为0的属性方法决定。

下面我们写一个简单的实例:

定义一个对象CTest,实现接口ITest,ITest又派生自IDispatch;ITest定义一个属性Item

第一步:先生成接口ITest及对象CTest

interface ITest: IDispatch {
        [id(00000000), propget]
        HRESULT Item(
                        [out, retval] VARIANT* pVariantReturn);
          };

class ATL_NO_VTABLE CTest :
 public CComObjectRootEx ,
 public CComCoClass,
 public IDispatchImpl
{
public:

      ........................

 public:

 // ITest Methods
public:

 STDMETHOD(get_Item)(VARIANT * pVariantReturn)
 {
       CComVariant pvResult=L"This is a test";
       pvResult.Detach(pVariantReturn);
       return S_OK;
 }

第二步:

在其他要实现的对象中
STDMETHOD(get_Item)(BSTR bstrVar, LPDISPATCH * ppObjReturn)

      CComObject *pTest;
      CComObject ::CreateInstance(&pTest);
     
      return pTest->QueryInterface(IID_IDispatch,(void**)ppObjReturn);
     


 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值