最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

C++ com編程學(xué)習(xí)詳解

 更新時間:2021年09月22日 16:35:56   作者:不會寫代碼的絲麗  
這篇文章主要介紹了C++ COM編程的學(xué)習(xí)過程,在C++中,可以使用抽象基類來實現(xiàn)COM接口,需要的朋友可以參考下,希望能夠給你帶來幫助

COM簡介

COM全程為component object model ,是一個二進制標(biāo)準(zhǔn)可以用于跨語言調(diào)用dll模塊或者實現(xiàn)組件化以及復(fù)用。com不僅可以用在單個操作系統(tǒng)也可以用在跨服務(wù)上,在很多大型軟件如wps,office你都會看到它的身影。

比如java中調(diào)用規(guī)范如下:

JAVA COM編程

你可能會在電腦出現(xiàn)缺少dll情況,一種修復(fù)方式下載dll然后調(diào)用regsvr32.exe xxx.dll即可修復(fù)。

在這里插入圖片描述

上面便是COM組件的注冊,本質(zhì)是把這個dll信息注冊到注冊表中,以便其他系統(tǒng)軟件可以加載。

flutter也提供相關(guān)接口封裝flutter相關(guān)文檔鏈接

本文主要介紹c++下使用com規(guī)范編程。

為什么需要COM?僅僅是為調(diào)用dll何必引用一個如此復(fù)雜的概念?

1.假設(shè)某個exe升級其中一個dll想要僅發(fā)布dll而不是是發(fā)布主體文件,在大多數(shù)情況下是沒有任何問題的。但是在不同編譯器編譯(或者同編譯器不同版本)出的主體exe和dll是有可能出現(xiàn)內(nèi)存布局上的差異引起的奔潰。startoverflow上的一個經(jīng)典問題

2.跨語言調(diào)用,比如c語言以\0結(jié)束,但是不是所有語言字符串定義都是如此。

3.跨進程或者跨服務(wù)上調(diào)度dll函數(shù)

4.dll代碼復(fù)用 與共享

COM 規(guī)范

com使用idl文件去定義dll函數(shù)或者接口,之后用midl編譯器生產(chǎn)對應(yīng)的頭文件,開發(fā)者再利用其去實現(xiàn)接口。

接口有自己的標(biāo)識符號IID 防止與其他人的接口在名字上沖突.

在這里插入圖片描述

編譯后的某個頭文件你會看到IID_XXXXX 如下所示

在這里插入圖片描述

如果說IID是為了標(biāo)識一個接口,那么應(yīng)該還有一個ID去用于標(biāo)識實現(xiàn)類,這個實現(xiàn)類的id我們稱為CLSID,CLSID會在注冊表映射一個dll信息,也就是我們可以用個這個CLSID可以在注冊表中尋找到dll文件信息。

s在這里插入圖片描述

tip:一個實現(xiàn)類可能會包含多個接口

更多idl語法可以參閱官方指南:

https://docs.microsoft.com/en-us/windows/win32/com/defining-com-interfaces

https://bbs.csdn.net/topics/30094944?list=34484

使用ATL編寫一個com共享dll庫 使用管理員權(quán)限運行vs(編譯dll會自動調(diào)用regsvr32注冊到注冊表,但是需要權(quán)限)

首先創(chuàng)建一個ATL工程,創(chuàng)建后你會看到一個idl文件

在這里插入圖片描述

新建一個接口如下:

在這里插入圖片描述

在這里插入圖片描述

上面ProgId一個可選項,它的作用是提供了另一種方式尋找注冊過的dll。

在這里插入圖片描述

完成后我們的IDL會自動產(chǎn)生相關(guān)語法到文件中

s在這里插入圖片描述

同時會創(chuàng)建對應(yīng)的頭文件和c文件如下

在這里插入圖片描述

此時我們到類視圖添加一個接口方法

在這里插入圖片描述

添加后idl同樣會如下圖所示生產(chǎn)對應(yīng)的語法

在這里插入圖片描述

對應(yīng)的c文件自行實現(xiàn)接口(最后一個參數(shù)作為返回參數(shù))

在這里插入圖片描述

編譯后會產(chǎn)生 工程名_i.c和工程名.h文件,并且自動會將dll注冊注冊表中。

將上訴兩個文件拷貝其他使用工程中(注意我們并沒有拷貝dll)如下圖所示:

在這里插入圖片描述

然后再調(diào)代碼如下所示調(diào)用:

#include <iostream>
#include"FMYALTFOUR_i.h"
int main()
{
	//初始化
	CoInitialize(NULL);
	IClassFactory *pFactory = NULL;
	//通過CLSID從注冊表中查到dll位置并加載 然后返回一個類工廠
	HRESULT hr = CoGetClassObject(CLSID_IfmyMathHelper,CLSCTX_INPROC_SERVER,
		NULL,
		IID_IClassFactory, (void**)&pFactory
		);
	//利用類工廠得到一個接口實例化對象
	IIfmyMathHelper * pSuperMath = NULL;
	pFactory->CreateInstance(NULL, IID_IIfmyMathHelper, (void**)&pSuperMath);
	long ret;
	pSuperMath->add(1, 2, &ret);
	//反初始化
	CoUninitialize();
}

當(dāng)然這是其中一種調(diào)用方式,還有一種是預(yù)留給vb這類語言調(diào)用的實現(xiàn)這種方式你不需要拷貝上訴兩個文件,但是創(chuàng)建接口必須勾選接口雙重。

int main()
{
	//初始化
	CoInitialize(NULL);
	HRESULT hr;
	GUID clsid;
	IUnknown FAR* punk;
	IDispatch FAR* pdisp = (IDispatch FAR*)NULL;
	//通過progId反向查找出clsid 去加載dll
	hr = CLSIDFromProgID(OLESTR("progIdfmyMathHelper.1"), &clsid);
	IDispatch* pDispatch = NULL;
	hr = CoCreateInstance(clsid, NULL, CLSCTX_INPROC_SERVER, IID_IDispatch, (void**)&pDispatch);
	LPOLESTR szMember[1] = { (LPOLESTR)OLESTR("add") };
	DISPID dipid[1] = { 0 };
	hr=pDispatch->GetIDsOfNames(IID_NULL, szMember, 1, LOCALE_USER_DEFAULT, dipid);
	CComVariant vars[2];
	DISPPARAMS args = { NULL,NULL,0,0 };
	vars[0] = 2;
	vars[1] = 1;
	args.cArgs = 2;
	args.rgvarg = vars;
	CComVariant Ret;
	hr=pDispatch->Invoke(dipid[0], IID_NULL, LOCALE_USER_DEFAULT, DISPATCH_METHOD,
		&args, &Ret,NULL,NULL
		);
	std::cout << "Hello World!\n" << Ret.lVal;
	//反初始化
	CoUninitialize();
}

COM 原理學(xué)習(xí)

regsvr32.exe xxx.dll 本質(zhì)作用會加載dll然后調(diào)用如下幾個函數(shù),dll應(yīng)該根據(jù)規(guī)范在對應(yīng)函數(shù)中實現(xiàn)對應(yīng)的邏輯(比如DllRegisterServer中應(yīng)當(dāng)實現(xiàn)注冊信息到注冊表中)

在這里插入圖片描述

上面幾個函數(shù)在你創(chuàng)建atl工程的def文件可以看到.

我們接下來看看注冊表中的信息,dll首先會利用CLSID的數(shù)值在如下注冊表路徑創(chuàng)建對應(yīng)的信息
計算機\HKEY_CLASSES_ROOT\WOW6432Node\CLSID\{xxxxxxxxxxx}

在這里插入圖片描述

在這里插入圖片描述

如果ProgId會在如下圖位置創(chuàng)建額外的信息,主要用于提供其他方式尋找到dll信息。

在這里插入圖片描述

其中32位系統(tǒng)和64系統(tǒng)可能路徑有所不同可以參考如下鏈接所示

How to use the Regsvr32 tool and troubleshoot Regsvr32 error messages

自己模擬atl的實現(xiàn)代碼: https://github.com/Zjvngvn/studyCom.git

ActiveX

ActiveX也是基于Com實現(xiàn)的一個UI組件庫。你可以在ATL下輕松的創(chuàng)建對應(yīng)控件,然后在其他工程插入即可

在這里插入圖片描述

總結(jié)

本篇文章就到這里了,希望能夠給你帶來幫助,也希望您能夠多多關(guān)注腳本之家的更多內(nèi)容!

相關(guān)文章

  • C語言代碼實現(xiàn)猜數(shù)字

    C語言代碼實現(xiàn)猜數(shù)字

    這篇文章主要為大家詳細介紹了C語言代碼實現(xiàn)猜數(shù)字,文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2020-11-11
  • Qt實現(xiàn)進程間通信

    Qt實現(xiàn)進程間通信

    這篇文章主要為大家詳細介紹了Qt實現(xiàn)進程間通信,文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2022-08-08
  • C調(diào)用C++代碼的方法步驟

    C調(diào)用C++代碼的方法步驟

    本文主要介紹了C調(diào)用C++代碼的方法步驟,文中通過示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2021-11-11
  • C語言鏈表實現(xiàn)通訊錄系統(tǒng)課程設(shè)計

    C語言鏈表實現(xiàn)通訊錄系統(tǒng)課程設(shè)計

    這篇文章主要為大家詳細介紹了C語言鏈表實現(xiàn)通訊錄系統(tǒng)課程設(shè)計,文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2022-06-06
  • C++類常量和類枚舉

    C++類常量和類枚舉

    這篇文章主要介紹了C++類常量和類枚舉,給類當(dāng)中定義一些常量,可以給所有類的對象使用,比如說我們在類當(dāng)中定義一個數(shù)組,希望可以定義一個常量,用來初始化數(shù)組的長度,那么下面我i嗎就來看看過程當(dāng)如何吧
    2022-01-01
  • C語言魔塔游戲的實現(xiàn)代碼

    C語言魔塔游戲的實現(xiàn)代碼

    這篇文章主要介紹了C語言魔塔游戲的實現(xiàn)代碼,文中通過示例代碼介紹的非常詳細,對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2020-02-02
  • 深入sizeof的使用詳解

    深入sizeof的使用詳解

    本篇文章是對sizeof的使用進行了詳細的分析介紹,需要的朋友參考下
    2013-05-05
  • C++實現(xiàn)簡單版通訊錄管理系統(tǒng)

    C++實現(xiàn)簡單版通訊錄管理系統(tǒng)

    這篇文章主要為大家詳細介紹了C++實現(xiàn)簡單版通訊錄管理系統(tǒng),文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2022-06-06
  • C語言宏定義的擴展定義講解

    C語言宏定義的擴展定義講解

    這篇文章主要介紹了C語言宏定義的擴展,宏定義是C語言提供的三種預(yù)處理功能的其中一種,這三種預(yù)處理包括:宏定義、文件包含、條件編譯
    2022-12-12
  • 深入理解C++的對象模型

    深入理解C++的對象模型

    本文在介紹C++使用的對象模型之前,先介紹了2種對象模型:簡單對象模型(a simple object model)和表格驅(qū)動對象模型(a table-driven object model),這樣介紹對后面的內(nèi)容更有幫助,有需要的小伙伴們可以參考學(xué)習(xí)。
    2016-08-08

最新評論

湛江市| 龙门县| 武川县| 景宁| 会东县| 平山县| 蕲春县| 全州县| 鄯善县| 外汇| 九江县| 威海市| 眉山市| 宁乡县| 黄陵县| 永平县| 庆城县| 祥云县| 扎赉特旗| 龙岩市| 大庆市| 石棉县| 宜黄县| 崇信县| 麦盖提县| 巴里| 沽源县| 正安县| 辽源市| 平昌县| 阳高县| 安徽省| 蒲城县| 海盐县| 雷波县| 台东市| 虹口区| 沂源县| 波密县| 电白县| 广元市|