亚洲欧美日韩熟女|做爱高潮视频网址|国产一区二区三级片|国产Av中文字幕www.性色av|亚洲婷婷永久免费|国产高清中文字幕|欧美变态网站久re视频精品|人妻AV鲁丝第一页|天堂AV一区二区在线观看|综合 91在线精品

微軟的COM中GUID和UUID、CLSID、IID

2023-04-12


當(dāng)初微軟設(shè)計(jì)com規(guī)范的時候,有兩種選擇來保證用戶的設(shè)計(jì)的com組件可以全球唯一:


第一種是采用和Internet地址一樣的管理方式,成立一個管理機(jī)構(gòu),用戶如果想開發(fā)一個COM組件的時候需要向該機(jī)構(gòu)提出申請,并交一定的費(fèi)用。


第二種是發(fā)明一種算法,每次都能產(chǎn)生一個全球唯一的COM組件標(biāo)識符。


第一種方法,用戶使用起來太不方便,微軟采用第二種方法,并發(fā)明了一種算法,這種算法用GUID(Globally Unique Identifiers)來標(biāo)識COM組件,GUID是一個128位長的數(shù)字,一般用16進(jìn)制表示。算法的核心思想是結(jié)合機(jī)器的網(wǎng)卡、當(dāng)?shù)貢r間、一個隨即數(shù)來生成GUID。從理論上講,如果一臺機(jī)器每秒產(chǎn)生10000000個GUID,則可以保證(概率意義上)3240年不重復(fù)。


GUID的例子: 54BF6567--1007--11D1--B0AA--444553540000


HKEY_CLASSES_ROOT\CLSID\{002B9E07-2E10-438F-AF1E-40E6A96F1EE4}


在微軟的COM中GUID和UUID、CLSID、IID是一回事,只不過各自代表的意義不同:


UUID : 代表COM


CLSID : 代表COM組件中的類


IID :代表COM組件中的接口


在程序中,實(shí)際對象數(shù)據(jù)對應(yīng)的處理程序路徑string往往不盡相同,比如有的放C盤有的D盤,微軟想出了一個解決方案,那就是不使用直接的路徑表示方法,而使用一個叫 CLSID的方式間接描述這些對象數(shù)據(jù)的處理程序路徑。


CLSID 其實(shí)就是一個號碼,CLSID 的結(jié)構(gòu)定義如下:


typedef struct _GUID {
DWORD Data1; // 隨機(jī)數(shù)
WORD Data2; // 和時間相關(guān)
WORD Data3; // 和時間相關(guān)
BYTE Data4[8]; // 和網(wǎng)卡MAC相關(guān)
} GUID;


typedef GUID CLSID; // 組件ID
typedef GUID IID; // 接口ID
#define REFCLSID const CLSID &


// 常見的聲明和賦值方法
CLSID CLSID_Excel = {0x00024500,0x0000,0x0000,{0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46}};
struct __declspec(uuid("00024500-0000-0000-C000-000000000046")) CLSID_Excel;
class DECLSPEC_UUID("00024500-0000-0000-C000-000000000046") CLSID_Excel;
// 注冊表中的表示方法
{00024500-0000-0000-C000-000000000046}


如果使用開發(fā)環(huán)境編寫組件程序,則IDE會自動幫你產(chǎn)生 CLSID;


可以用函數(shù) CoCreateGuid() 產(chǎn)生 CLSID;


使用"vc目錄\Common\Tools\GuidGen.exe"工具產(chǎn)生GUID


每一個COM組件都需要指定一個 CLSID,并且不能重名。它之所以使用16個字節(jié),就是要從概率上保證重復(fù)是“不可能”的。但是,微軟為了使用方便,也支持另一個字符串名稱方式,叫 ProgID。。由于 CLSID 和 ProgID 其實(shí)是一個概念的兩個不同的表示形式,所以我們在程序中可以隨便使用任何一種。
下面是 CLSID 和 ProgID 之間的轉(zhuǎn)換方法和相關(guān)的函數(shù):



函數(shù)


功能說明


CLSIDFromProgID()、CLSIDFromProgIDEx()


由 ProgID 得到 CLSID。沒什么好說的,你自己都可以寫,查注冊表貝


ProgIDFromCLSID()


由 CLSID 得到 ProgID,調(diào)用者使用完成后要釋放 ProgID 的內(nèi)存(注5)


CoCreateGuid()


隨機(jī)生成一個 GUID


IsEqualGUID()、IsEqualCLSID()、IsEqualIID()


比較2個ID是否相等


StringFromCLSID()、StringFromGUID2()、StringFromIID()


由 CLSID,IID 得到注冊表中CLSID樣式的字符串,注意釋放內(nèi)存


客戶端軟件和組件之間的調(diào)用如下:



容器 協(xié)商部分


組件 應(yīng)答部分


1


根據(jù)CLSID啟動組件 。


CoCreateInstance()


生成對象,執(zhí)行構(gòu)造函數(shù),執(zhí)行初始化動作。


2


你有IUnknown接口嗎?


有,給你!


3


恩,太好了,那么你有IPersistStorage接口嗎?(注9)


IUnknown::QueryInterface(IID_IPersistStorage...)


沒有!


4


真差勁,連這個都沒有。那你有IPersistStreamInit接口嗎?(注10)


IUnknown::QueryInterface(IID_IPersistStreamInit...)


哈,這個有,給!


5


好,好,這還差不多。你現(xiàn)在給我初始化吧。


IPersistStreamInit::InitNew()


OK,初始化完成了。


6


完成了?好!現(xiàn)在你讀數(shù)據(jù)去吧。


IPersistStreamInit::Load()


讀完啦。我根據(jù)數(shù)據(jù),已經(jīng)在窗口中顯示出來了。


7


好,現(xiàn)在咱們各自處理用戶的鼠標(biāo)、鍵盤消息吧......


......


8


哎呀!用戶要保存退出程序了。你的數(shù)據(jù)被用戶修改了嗎?


IPersistStreamInit::IsDirty()


改了,用戶已經(jīng)修改啦。


9


那好,那么用戶修改后,你的數(shù)據(jù)需要多大的存儲空間呀?


IPersistStreamInit::GetSizeMax()


恩,我算算呀......好了,總共需要500KB。


10


暈,你這么個小玩意居然占用這么大空間?!......好了,你可以存了。


IPersistStreamInit::Save()


謝謝,我已經(jīng)存好了。


11


恩。拜拜了您那。(注11)


IPersistStreamInit::Release();IUnknown::Release()


執(zhí)行析構(gòu)函數(shù),刪除對象。


12


我自己也該退出了......


PostQuitMessage()





本文僅代表作者觀點(diǎn),版權(quán)歸原創(chuàng)者所有,如需轉(zhuǎn)載請?jiān)谖闹凶⒚鱽碓醇白髡呙帧?/p>

免責(zé)聲明:本文系轉(zhuǎn)載編輯文章,僅作分享之用。如分享內(nèi)容、圖片侵犯到您的版權(quán)或非授權(quán)發(fā)布,請及時與我們聯(lián)系進(jìn)行審核處理或刪除,您可以發(fā)送材料至郵箱:service@tojoy.com