`
阅读更多

3.1 ATL 的基本特征

描述:ATL提供了实现基于COM组件内核的支持.下面是ATL所提供的一些功能

1)AppWizard,它负责创建起始的ATL工程
2)Object Wizard(对象向导),它为基本的COM组件创建代码
3)对低级别的COM功能的内置式支持,如IUnknown,类工厂和自注册(self-registration)功能
4)ATL支持Microsoft的接口定义语言(Interface Definition Language,IDL),它提供了对自定义的Vtable接口的调度支持,以及通过类型库进行自描述的功能
5)ATL支持IDispatch(自动化)和双向接口(dual-interface)
6)ATL可以支持开发效率更高的ActiveX控件
7)ATL提供对基本的视窗功能的支持


3.2 ATL 和 MFC

描述:ATL的目标是为了简化小规模的,基于COM组件的创建.MFC则基于Windows应用程序的开发速度,它通常带有大量的GUI.两者的相似之处是对OLE和ActiveX的支持


3.3 ATL 框架结构概述

描述:ATL是一个C++的类库或框架,它处理基于COM程序开发中的很多琐碎的例行工作,如,COM组件需要一个DLL或EXE宿主,而组件也需要一个类工厂.

3.3.1 ATL 的实现

1)ATL是一个基于模板的框架,它将ATL的实现作为你组件实现里的一部分.因此,你只需要在程序里包含头文件,即可获得ATL内建的功能.
2)ATL的设计目标是为了建立小型的,独立的组件.ATL提供了几个选项处理可执行文件变大的问题.如:
// stdafx.h
#define _ATL_APARTMENT_THREADED
#include <atlbase.h>
#include <atlcom.h>
....

// stdafx.cpp
#include "stdafx.h"

// include ATL's implementation code
#include <atlimpl.cpp>

// Yourimplementation.cpp
#include "stdafx.h"

stdafx文件包含了工程类型的基本要求,所以需要把它包含在你的实现文件里
通过ATLIMPL.CPP大部分ATL的实现都成为工程的一个显示部分,它的代码也变成你的可执行文件的一部分

  ATL 的实现文件
文件名称    说明
ATLBASE.H   ATL工程的基本包含文件
ATLCOM.H   所有的ATL工程都必须包含ATLCOM.H,因为该文件提供了ATL的大部分基本行为
ATLIMPL.CPP   在ATLBASE.H和ATLCOM.H里声明的类和方法的实现代码
ATLCTL.H,ATLCTL.CPP  ATL对ActiveX控件所提供的支持,若使用ATL的控件支持,应包含它们
ATLWIN.H,ATLWIN.CPP  ATL对视窗和对话框的支持
STATREG.H,STATREG.CPP  ATL的注册组件的实现文件
ATLIFace.IDL,ATLIFACE.H  ATL的注册器组件的支持文件,头文件里包含了输出,该输出是通过MIDL编译器运行IDL的结果

3)ATL实现一些基本的API是在一个名为ATL.DLL的模块里进行的.它提供ATL类的辅助函数.
4)如果定义了ATL_DLL_符号变量,工程将依赖于ATL.DLL文件.若没有,ATLIMPL.CPP文件将把实现作为模块的一部分包含进来


3.3.2 组件的宿主支持

1)ATL在它的CComModule类里封装了一个组件的宿主支持.ATL对开发者掩盖了这两种宿主类型(dll或exe)之间的大多数差别.


3.3.3 对IUnknown的支持

1)ATL的IUnknown实现对理解在实现中究竟应该使用哪个宏至关重要.


3.3.4 对类工厂的支持

1)CComClassFactory提供了对基本的类工厂的支持
2)CComClassFactory2对获得许可的类工厂提供支持
3)CComClassFactorySingleton为单元素类工厂提供支持


3.3.5 对COM程序开发的其他方面的支持

COM的功能项    ATL的支持类
ActiveX控件   CComControl,IOleControlImpl,IOleObjectImpl 等都支持控件开发
自动化(Automation)  IDispatchImpl处理自动化和双向接口
COM的数据类型   CComBSTR 和 CComVariant
接口指针的管理   CComPtr 和 CComQIPtr
错误处理   ISupportErrorInfoImpl 和CComObject
连接点(Connection points) IConnectionPointContainerImpl 和 IConnectionPointImpl
异步属性下载   CBindStatusCallback
自注册(self-registration) ATL的注册对象(Register object,Iregistrar)提供自注册功能
视窗和对话框   CWindow,CWindowImpl,CDialogImpl,CMessageMap


3.4.4 接口

1)自定义(custom) -- 即标准的Vtable接口
2)双向(dual)  -- 它既实现了一个Vtable接口,也实现了标准的自动化接口.

3.4.5 集合

1)集合(Aggregation)是一个COM技术,它使得一个组件可以兼并或复用组件的功能.
2)内部组件必须可以通过它的IUnknown实现来显示支持该技术


3.4.6 对ISupportErrorInfo的支持

1)提供一个具有健壮性的,服务器到客户机(server-to-client)的错误汇报机制.


3.4.7 对连接点的支持

1)连接点(Connection Points)使一个客户程序和服务器程序可以在对等的基础上彼此进行通讯


2.4.8 自由线程调度器

1)自由线程调度(Free-Threaded Marshaling)提供了在单进程的线程里以默认的方式对接口指针进行线程之间的参数调度


3.7 接口定义语言

描述: Microsoft的接口定义语言(Interface Definition Language,IDL)是基于DCE RPC规范之上的,通常IDL是用来描述远程进程调用接口(Remote Procedure Call Interface)的.但它包含了对基于COM接口的支持,IDL的主要职能是用来以一种与语言无关的方法来定义一个组件的接口(它的方法和参数),使客户可以使用该定义.

1)IDL使用一种C类型的语法,示例1

// Chapter3_Server.idl:IDL source for Chapter3_Server.dll

// The MIDL tool processes this file to
// produce the type library(Chapter3_Server.lib) and marshaling code

import "oaidl.idl";
import "ocidl.idl";

// 第一个接口
[
 object,
 uuid(8812899C-1CC9-11D1-883A-44455354000),
 helpstring("IMath Interface"),
 pointer_default(unique)
]

interface IMath:IUnknown
{
 [helpstring("method Add")]
   HRESULT Add(long lOp1,long lOp2,long *plResult);
 [helpstring("method Subtract")]
   HRESULT Substract(long lOp1,long lOp2,long *plResult);
 [helpstring("method Multiply")]
   HRESULT Multiply(long lOp1,long lOp2,long *plResult);
 [helpstring("method Divide")]
   HRESULT Divide(long lOp1,long lOp2,long *plResult);
};

// 第二个接口

[
 object,
 uuid(6AF3DF1E-C48F-11D0-A769-D477A4000000),
 helpstring("IAdvancedMath Interface"),
 pointer_default(unique)
]

interface IAdvancedMath:IUnknown
{
 HRESULT Factorial([in] short sFact,[out,retval]long*pResult);
 HRESULT Fibonacci([in] short sFib,[out retval]long *pResult);
};

// 链接库

[
 uuid(A751FA9F-EE00-4733-8196-FDDA21B36F63),
 version(1.0),
 helpstring("ATLSERVER 1.0 Type Library")
]

library ATLSERVERLib
{
 importlib("stdole32.tlb");
 importlib("stdole2.tlb");

};

属性包括在括号([])之内,它们提供了关于后面定义语句的附加信息,比如IMath接口的定义开始于三个属性定义.

2)对象的属性指定了你所描述的是一个COM的自定义接口,而不是一个基于DCE/RPC的接口.IDL也可以描述RPC接口
[
 object,
 uuid(8812899C-1CC9-11D1-883A-44455354000),
 helpstring("IMath Interface"),
 pointer_default(unique)
]

3)uuid 指明你的接口的GUID,helpstring 指明了一些对象浏览器可以显示的文本.
4)pointer_default 属性为任何一个在接口内定义的指针设定了默认的指针属性.unique使指针所指向的内存不被应用程序的其他代码所更改.

5) 示例2:接口定义

interface IMath:IUnknown
{
 [helpstring("method Add")]
   HRESULT Add([in] long lOp1,[in] long lOp2,[out retval] long *plResult);
 [helpstring("method Subtract")]
   HRESULT Substract([in] long lOp1,[in] long lOp2,[out retval] long *plResult);
 [helpstring("method Multiply")]
   HRESULT Multiply([in] long lOp1,[in] long lOp2,[out retval] long *plResult);
 [helpstring("method Divide")]
   HRESULT Divide([in] long lOp1,[in] long lOp2,[out retval] long *plResult);
};

关键字 in 和 out 指定了参数传递的方向.关键字 retval 指明了参数应该被当作方法的返回值

6)示例3:类型库描述

[
 uuid(8812698E-1CCB-11D1-883A-444553540000),
 version(1.0),
 helpstring("Chapter3_Server 1.0 Type Library")
]

library CHAPTER3_SERVERLIB
{
 importlib("stdole32.tlb");
 importlib("stdole2.tlb");
 [
  uuid(8812699D-1CC8-11D1-883A-444553540000),
  helpstring("Math Class")
 ]
 coclass Math
 {
  [default] interface IMath;
  interface IAdvancedMath;
 };
};
属性代码段从整体上描述了类型库,它有一个GUID,一个版本号,一个帮助字符串
关键字 library 指定了库的名称,并通常把指定的宿主文件的定义都包含进来,coclass 指定了独立的组件以及它们支持的接口

7) 基本的IDL关键字

关键字   说明
object  开始对一个基于COM的自定义接口进行定义,object 后面跟随了几个用于描述附加接口功能的属性
uuid  唯一定义给定接口,类型库或组件类的GUID
helpstring 指定一个处理组件和接口浏览器显示内容的字符串
interface 指定接口的名称.该名称随后被用在coclass部分里来指定组件支持的接口
coclass  描述又某一给定的COM对象所支持的接口.而GUID指定了组件本身.
default  指定了默认的组件接口.一个组件对象可以拥有至多两个默认接口.一个针对源,一个针对可编程宿接口
in/out/retval 它们针对方法的调用,它指定了每一个参数的传递方向.retval关键字说明了参数应该被当作方法的返回值处理

8)IDL文件经过MIDL编译器处理后产生的重要文件

a.编译IDL文件是为了生成C++头文件,在该头文件里声明并定义了接口,类标识符和工程的接口标识符.
b.IDL文件被编译成为二进制格式,即类型库.组件用户可以通过检查该类型库(.TLB)来确定他们该如何访问该库,并与之交互
c.IDL文件生成了一系列C文件和一个make文件,并可根据它们来创建代理/占位DLL文件.该DLL文件为组件的接口提供了参数调度方面的支持

3.8 ATL 工程的建立

3.8.1 ATL的基本宿主支持:CComModule

1)ATL的CComModule 类为 COM 对象提供了基本的宿主支持,每一个COM对象都必须在Windows进程中执行.

3.8.2 BEGIN_OBJECT_MAP 和 OBJECT_ENTRY 宏

1)这些宏建立起有个CLSID表和它们自己相关的ATL实现类(即组件)
BEGIN_OBJECT_MAP(ObjectMap)
 OBJECT_ENTRY(CLSID_Main,CMath)
END_OBJECT_MAP()

2)ATL通过CLSID表,并使用宿主文件中每一个组件信息来刷新注册表.类的UpdateRegistry方法被调用.
3)宏DECLARE_REGISTRY自动实现了UpdateRegistry.
4)对象映射生成了某一组件的实例,即它提供了组件的类工厂.宏展开如下:

#define BEGIN_OBJECT_MAP(x) static _ATL_OBJMAP_ENTRY x[] = {
#define OBJECT_ENTRY(clsid,class) {
 &clsid,
 &class::UpdateRegistry,
 &class::_ClassFactoryCreatorClass::CreateInstance, // 返回类工厂实例
 &class::_CreatorClass::CreateInstance,   // 返回组件类本身实例
 NULL,0,&class::GetObjectDescription},
#define END_OBJECT_MAP() {NULL,NULL,NULL,NULL} };

3.8.3 CComModule

1)CComModule 位于ATLBASE.H 和 ATLIMPL.CPP 里.
  常用的CComModule方法
方法名称   说明
Init   初始化CComModule实例,它通常对内部的数据成员进行初始化并使该实例处于就绪状态,它最后将调用AtlModuleInit()
GetClassObject  仅在DLL宿主文件里使用,它创建组件类工厂的一个实例.即它提供了DLL宿主文件的DllGetClassObject函数的实现
RegisterClassObject 被用来注册一个可执行宿主文件的类工厂
RevokeClassObject 当EXE文件被关闭的时候,Revoke方法可以用来注销类工厂
Lock/Unlock  
RegisterServer  对出现在UnregisterServer宿主文件里的每一个组件添加或删除注册表项


3.8.4 ATL对组件的支持

1)每一个COM对象都必须支持IUnknown接口和其他公开其特定功能的接口
2)每一个COM对象也必须提供一个类工厂,从而客户应用程序才可以创建它
3)COM对象应该提供自注册功能

3.8.4.1 ATL对IUnknown的支持

3.8.4.2 CComObjectRootEx 和 CComObjectRootBase

1) 每一个将成为COM对象的ATL类都必须从CComObjectRootEx类里派生出来.
2)CComObjectRootEx间接地为组件提供了引用计数和QueryInterface支持
3)
class CComObjectRootBase
{
public:
 CComObjectRootBase()
 {
  m_dwRef = 0L;
 }
 
 static HRESULT WINAPI InternalQueryInterface(void * pThis,
    const _ATL_INTMAP_ENTRY * pEntries,
    REFIID iid,void ** ppvObject)
 {
  HRESULT hRes = AtlInternalQueryInterface(pThis,pEntries,id,ppvObject);
 }
 
 ULONG OuterAddRef()
 {
  return m_pOuterUnknown->AddRef();
 }
 
 ULONG OuterRelease()
 {
  return m_pOuterUnknown->Release();
 }
 
 HRESULT OuterQueryInterface(REFIID iid,void **ppvObject)
 {
  return m_pOuterUnknown->QueryInterface(iid,ppvObject);
 }
 
 union
 {
  long m_dwRef;
  IUnknown* m_pOuterUnknown;
 };
};

CComObjectRootBase 包含了引用计数变量,用来维护对象的外部接口引用

4)一个集合实例也必须要通过IUnknown方法来调用它的外部组件.CComObjectRootBase对组件里的集合提供了基本的支持
5)CComObjectRootEx为非集合的IUnknown方法提供了支持.

template <class ThreadModel>
class CComObjectRootEx:public CComObjectRootBase
{
public:
 typedef ThreadModel _ThreadModel;
 typedef _ThreadModel::AutoCriticalSection _CritSec;
 
 ULONG InternalAddRef()
 {
  return _ThreadModel::Increment(&m_dwRef);
 }
 
 ULONG InternalRelease()
 {
  return _ThreadModel::Decrement(&m_dwRef);
 }
 
 void Lock() { m_critsec.Lock();}
 void Unlock() {m_critsec.Unlock();}
 
private:
 _CritSec m_critsec;
}

3.8.4.3 CComObjectRoot 和线程管理

1)CComObjectRoot 定义
typedef CComObjectRootEx<CComObjectThreadModel> CComObjectRoot;

2)CComObjectThreadModel 的定义
// from ATLBASE.H
#if defined(_ATL_SINGLE_THREADED)
 typedef CComSingleThreadModel CComObjectThreadModel;
 typedef CComSingleThreadModel CComGlobalsThreadModel;
#elif defined(_ATL_APARTMENT_THREADED)
 typedef CComSingleThreadModel CComObjectThreadModel;
 typedef CComMultiThreadModel CComGlobalsThreadModel;
#else
 typedef CComMultiThreadModel CComObjectThreadModel;
 typedef CComMultiThreadModel CComGlobalsThreadModel;
#endif

3.8.5 AddRef 和 Release所在的位置

1)ATL通过CComObjectRootEx的内部和外部方法来管理引用的计数,CComObject中的类则处理对IUnknown方法实现
2)生成CMath类实例
IMath *pIMath = new CComObject<CMath>
3)实现math组件所必须的类

CComObjectBase
      |
      V
 CComObjectRoot         CComCoClass   IMath
      |       |      |
      V       V      V
      -----------------------------------------------
    CMath
      |
      V
       CComObject<CMath>
      
       基本的ATL实现
      
CComObjectRoot 提供了InternalAddRef,InternalRelease,InternalQueryInterface
CComCoClass 提供了对类工厂的支持
IMath,IAdvancedMath 提供了抽象的接口类

以上这些组合在一起生成了CMath类,ATL更深一步,为了创建实例,它使用CMath作为CComObject的模板参数,使CComObject从CMath中派生出来

3.8.6 CComObject

// from atlcom.h
template <class Base>
class CComObject:public Base
{
public:
 ...
 STDMETHOD_(ULONG,AddRef)(){return InternalAddRef();}
 STDMETHOD_(ULONG,Release)()
 {
  ULONG l = InternalRelease();
  if (l == 0)
   delete this;
  return l;
 }
 
 STDMETHOD(QueryInterface)(REFIID iid,void **ppvObject)
 {
  return InternalQueryInterface(iid,ppvObject);
 }
};

注意这里的CComObject的方法直接调用了由CComObjectRootEx实现的内部方法,从而它们不能支持集合.

3.8.8 ATL_NO_VTABLE

1)ATL_NO_VTABLE 等同于 __declspec(novtable),它告诉编译器不要为类生成或初始化一个Vtable结构.

3.8.9 ATL的类工厂支持:CComCoClass

1)CComCoClass 提供了类工厂支持,以及获取CLSID和组件错误信息的基本方法

// from MATH.H
class ATL_NO_VTABLE CMath:
 public CComObjectRootEx<CComSingleThreadModel>,
 public CComCoClass<CMath,&CLSID_Math>,
 public IMath,
 public IAdvancedMath
{
...
};

上面既需要提供你的实现类的名称,也需要通过CComCoClass的模板参数来提供组件的CLSID
模板展开:
class CComCoClass
{
public:
 DECLARE_CLASSFACTORY()
 DECLARE_AGGREGATABLE(CMath)
 typedef CMath _CoClass;
 static const CLSID& WINAPI GetObjectCLSID(){return &CLSID_Math;}
 static LPCTSTR WINAPI GetObjectDescription() {return NULL;}
 static HRESULT WINAPI Error(LPCOLESTR lpszDesc,
    const IID&iid = GUID_NULL,
    HRESULT hRes =0)
 {
  return AtlReportError(GetObjecCLSID(),lpszDesc,iid,hRes);
 }
 ...
};

2)CComCoClass 通过 DECLARE_CLASSFACTORY 为组件的类工厂提供支持.
3)ATL的OBJECT_ENTRY宏需要使用DECLARE_CLASSFACTORY.OBJECT_ENTRY宏为宿主文件中每一个组件建立一个构造函数映射表
4)DECLARE_CLASSFACTORY宏
#define DECLARE_CLASSFACTORY
 typedef CComCreator<CComObjectCached<CComClassFactory>> \
  _ClassFactoryCreatorClass;
5)DECLARE_AGGREGATABLE宏
#define DECLARE_AGGREGATABLE(x)
 typedef CComCreator2<CComCreator<CComObject<x>>,\
  CComCreator<CComAggObject<x>>> _CreatorClass;
  
6)_ClassFactoryCreatorClass 和 _CreatorClass 生成类包含了静态的CreateInstane方法用来创建类的实例

3.8.9.1 DECLARE_CLASSFACTORY 宏
// from ATLCOM.H
#define DECLARE_CLASSFACTORY()
 DECLARE_CLASSFACTORY_EX(CComClassFactory)
#define DECLARE_CLASSFACTORY_EX(cf) \
 typedef CComCreator<CComObjectCached<cf>> _ClassFactoryCreatorClass;
 
上面完全展开:
typedef CComCreator<CComObjectCached<CComClassFactory>> _ClassFactoryCreatorClass

1)ATL使用创建类来实际建立组件的实例,同时还使用创建类来建立组件的类工厂.
2)创建类通过CComObjectCached实现来建立起类工厂的实现,CComObjectCached的实现被存储在缓存里.

3.8.9.2 CComCreator

// from ATLCOM.H
template <class T1>
class CComCreator
{
public:
 static HRESULT WINAPI CreateInstance(void *pv,REFIID riid,LPVOID * ppv)
 {
  _ASSERTE(*ppv == NULL);
  HRESULT hRes = E_OUTOFMEMORY;
  T1 *p = NULL;
  p = new T1(pv);
  if (p != NULL)
  {
   p->SetVoid(pv);
   p->InternalFinalConstructAddRef();
   hRes = p->FinalConstruct();
   p->InternalFinalConstructRelease();
   if (hRes == S_OK)
    hRes = p->QueryInterface(riid,ppv);
   if (hRes != S_OK)
    delete p;
  }
  return hRes;
 }
};

静态方法CreateInstance创建了被指定为模板参数的类的实例

3.8.9.3 CComClassFactory

class CComClassFactory : public IClassFactory,
    public CComObjectRootEx<CComGlobalsThreadModel>
{
public:
 BEGIN_COM_MAP(CComClassFactory)
  COM_INTERFACE_ENTRY(IClassFactory)
 END_COM_MAP()
 //IClassFactory
 STDMETHOD(CreateInstance)(LPUNKNOWN pUnkOuter,REFIID riid,void **ppvObj);
 STDMETHOD(LockServer)(BOOL fLock);
 //helper
 void SetVoid(void *pv)
 {
  m_pfnCreateInstance = (_ATL_CREATORFUNC*)pv;
 }
 _ATL_CREATORFUNC* m_pfnCreateInstance;
};

m_pfnCreateInstance成员包含了一个指向其他创建类静态方法的指针,该指针为类工厂提供了组件的生成机制

3.8.9.4 CComCreator2 和 DECLARE_AGGREGATABLE

1)默认的CComCoClass为集合赋予了组件的支持

class CComCoClass
{
public:
 typedef CComCreator<CComObjectCached<CComClassFactory>> _ClassFactoryCreatorClass;
 DECLARE_AGGREGATABLE(CMath)
 typedef CMath _CoClass;
 ...
};

2)DECLARE_AGGREGATABLE宏
#define DECLARE_AGGREGATABLE(x) public:\
 typedef CComCreator2<CComCreator<CComObject<x>>,\
 CComCreator<CComAggObject<x>>> _CreatorClass;
 
3)CComCreator2的定义
template <class T1,class T2>
class CComCreator2
{
public:
 static HRESULT WINAPI CreateInstance(void *pv,REFIID riid,LPVOID *ppv)
 {
  _ASSERTE(*ppv == NULL);
  HRESULT hRes = E_OUTOFMEMORY;
  if (pv == NULL)
   hRes = T1::CreateInstance(NULL,riid,ppv);
  else
   hRes = T2::CreateInstance(pv,riid,ppv);
  return hRes;
 }
};

分享到:
评论

相关推荐

    ATL学习笔记.doc

    6. 从向导中选择“ATL” -&gt; “ATL简单对象” -&gt; “添加”。 7. 在ATL简单对象向导中,输入类的简称,如“FIRSTclass”,并自定义ProgID(例如:FirstCOM.math)。点击“完成”。 8. 在类视图中,选择新添加的接口...

    windows shell、atl、https学习笔记

    总的来说,这个学习笔记涵盖了Windows系统核心组件、C++组件开发技术以及网络通信安全的关键概念,是一份全面的IT技术学习资料。通过深入学习这些内容,你可以提升自己在Windows平台上的软件开发和网络安全能力。

    ATL——com学习笔记

    在ATL中,默认情况下,每个类都会有一个自动创建的类工厂。然而,在某些情况下,我们可能希望替换这个默认的类厂,以实现更加灵活或者自定义的功能。 #### 实现步骤 1. **定义自己的类工厂**:首先需要继承自`...

    com学习笔记

    在COM学习笔记中,主要涉及的是COM线程管理的概念,包括线程单元(Thread Apartments,简称TA)以及线程如何与COM对象交互。 线程单元是COM中管理线程与对象交互的核心机制。它是一个逻辑上的容器,确保同一单元内...

    Visual C++程序设计学习笔记(1-12 源码)

    本资源包含的是Visual C++程序设计的学习笔记,涵盖了从基础到进阶的12个章节的源代码,对于学习和理解C++编程,特别是使用Visual C++环境编程,具有极高的参考价值。 首先,我们来详细探讨一下Visual C++的关键...

    ATL_OFFICE_COM

    4. **新建 文本文档 (3).txt**: 这可能是一个文本文件,可能包含了代码片段、笔记或其他辅助信息。 通过学习这些资源,开发者可以深入了解ATL和Office COM插件的开发,从而创建出自己的定制化Word插件,提高办公...

    VC学习笔记及项目代码1

    【VC学习笔记及项目代码1】是一份涵盖了多个VC++编程关键领域的学习资源,包括了Win32 API、MFC(面向对象的)框架、COM(Component Object Model,组件对象模型)及其ATL(Active Template Library,活动模板库)...

    COM学习笔记和测试程序

    本学习笔记和测试程序旨在帮助你深入理解COM的工作原理和实践应用。 1. **COM基础概念** - **组件**: 在COM中,组件是实现了COM接口的二进制模块,可以是DLL或EXE。 - **接口**: 接口定义了组件对外提供的服务,...

    vc++技术内幕第四版(清华版)学习笔记

    《VC++技术内幕第四版(清华版)》是C++编程领域的一本经典著作,尤其对于深入理解Microsoft的Visual C++编译器和MFC框架有...这份学习笔记则将书中的精华内容进行了整理,便于读者查阅和复习,是一份宝贵的参考资料。

    MFC学习笔记加windows32

    1. MFC架构:MFC由几个关键部分组成,包括框架类、文档/视图结构、对话框、控件、GDI(图形设备接口)以及ATL(Active Template Library)等。其中,框架类如CWinApp、CDocument、CView等,提供了应用程序的基本结构...

    EMF 自学笔记5

    ### EMF自学笔记知识点详述 #### 一、EMF框架概述 EMF(Eclipse Modeling Framework)是Eclipse项目中的一个子项目,它提供了一套用于构建模型驱动的开发工具和应用程序的框架。EMF的主要目标是简化元数据驱动应用...

    学习mfc的视频笔记

    这篇“学习MFC的视频笔记”显然是针对想要了解或深入学习MFC的初学者设计的,提供了视频教程的笔记内容,旨在帮助初学者快速入门。 1. **MFC基础**:MFC的核心是它的框架,它包括了各种C++类,如CWinApp、CWnd、...

    Matlab学习笔记#01

    在一直以来的学习当中,与matlab这款软件多有接触,但一直没有系统化地研究学习一下这款软件,趁着闲暇之余,整理一下自己有关matlab知识。 matlab技术支持搜索网站 一些基本的符号 ans→answer inf→∞ eps→2.2204...

    个人整理的资料

    "MyLearn.chm"可能包含了作者的学习笔记、教程或项目案例,涵盖了作者在VC++学习过程中的各种理解和感悟。"STL.chm"则很可能是关于标准模板库(Standard Template Library,STL)的详细解释,STL是C++编程中不可或缺...

    matlab学习笔记

    这篇学习笔记主要涉及了几个关键概念,包括标量、矩阵的迹、矩阵维度的获取、单位矩阵的生成、决策变量的定义以及几个相关的函数应用。 1. **标量(Scalar)**:在数学和计算机科学中,标量是一个单一的数值,不...

    17--锂离子电池工艺流程介绍(ATL教材).pdf

    本文档《17--锂离子电池工艺流程介绍(ATL教材).pdf》详细介绍了锂离子电池的整个生产过程,涵盖了从材料选择到最终成品测试的各个阶段,为锂电行业提供了一份宝贵的工艺教材。 锂离子电池的生产工艺流程可以划分...

    YearUp:在 Year Up ATL 创建的文件的存储库

    8. **学习资源**:除了代码,"YearUp-master"可能还包括学习笔记、教程链接、问题解答等辅助学习资料。 9. **团队协作**:Year Up的项目可能涉及多人合作,因此可能包含关于团队分工、沟通和协作的最佳实践。 10. ...

    matlab学习笔记:如何在matlab中如何自定义函数和匿名函数

    matlab的程序语言在拓展性上没有C++齐全,但也足够应付一些简单的程序,而且比C++更易于学习。 input():数据的输入函数。 disp():数据的输出函数。 pause(延迟时间):延迟函数。 其余的程序语句和C++大同小异,当然...

Global site tag (gtag.js) - Google Analytics