所謂內省是指物件導向語言的一種在執行期間查詢物件資訊的能力, 比如如果該語具有執行期間檢查物件型別的能力,那麼我們稱它是型別內省(type intropection
)的,型別內省可以用來實施多型。
c++的內省比較有限,它僅支援上面所說的型別內省, c++的型別內省是通過執行時型別識別(rtti
)(run-time type information
)中的typeid
以及dynamic_case
關鍵字來實現的,舉例說明:
// rabbit 派生於 animal, jump為虛函式
if ( rabbit *p = dynamic_case(obj))
//我們還可以通過typeid萃取到物件的型別資訊,比如物件的名稱
std::cout
<< typeid(obj).name() << std::endl
qt拓展了c++的內省機制,(實際上,它並沒有採用c++的rtti),而是提供了更為強大的元物件(meta object
)機制,來實現內省。接下來,就讓我們看看,qt是如何擴充套件c++內省機制的。
要深刻理解qt的內省機制,首先理解qobject
,qobject
類是整個qt物件模型的心臟,qt物件模型最為核心的功能是提供一種無縫的物件通訊機制,即就是我們所熟知的訊號和槽。qobject
主要有三大職責: 記憶體管理、內省(intropection
)與事件處理。本文將集中在在內省的討論。以下**介紹了qobject
類提供的內省方法:
//每個物件可以通過qobject::setobjectname()和qobject::objectname()設定、取得類的例項的名字
obj.setobjectname("instancename");
qstring name1 = obj.objectname(); // return instancename
//每個物件還可以通過它的元物件classname方法得到類的名字
//每個物件可以通過qobject::inherits方法來查詢是否對前物件類派生於量乙個類
bool isherited = obj.inherits("qobject"); // returns true
isherited = obj.inherits("qwideget"); // returns true
讓我們再來一下qobject::inherits
方法的底層實現:
inline
bool inherits(const
char *classname) const
原來,qobject::inherits
是通過qt_metacast()
這個虛函式實現的, 事實上每個qobject
的派生類都必須實現metaobject()
以及其他qt_metacall()
方法,從而滿足自省方法classname
,inherits
等方法的呼叫(當然還有其他用途)。
而所有有關派生從qobject
的子類中的內省方法無須有使用者實現,使用者只要在類中宣告巨集q_object
即可,qt的元物件編譯器(moc
)負責實現派生qobject
的子類中的內省方法。
// defined at ..\qt\src\corelib\kernel\qobjectdefs.h
/* tmake ignore q_object */
#define q_object \
public: \
q_object_check \
static
const qmetaobject staticmetaobject; \
q_object_getstaticmetaobject \
virtual
const qmetaobject *metaobject() const; \
virtual
void *qt_metacast(const
char *); \
qt_tr_functions \
virtual
int qt_metacall(qmetaobject::call, int, void **); \
此外,所有的qt widgets
類均繼承自qobject
,qobject
所提供的iswidgettype
自省方法可以很方便讓qobject
子物件查詢自己是否是wideget
, 而且它會比qobject_cast(obj)
或者obj->inherits
快很多。原因qobject_cast()
和inherits()
都是借助元物件系統來實現其功能的,iswidgettype()
是qobject
本身的標誌位得以實現。
struct
q_core_export qmetaobject
上述方法主要是實現對元物件表的訪問及其操作,元物件表(由moc
實現)例項如下所示:
// defined at ..\qt\src\corelib\kernel\qobjectdefs.h
/* tmake ignore q_object */
#define q_object \
public: \
q_object_check \
static
const qmetaobject staticmetaobject; \
q_object_getstaticmetaobject \
virtual
const qmetaobject *metaobject() const; \
virtual
void *qt_metacast(const
char *); \
qt_tr_functions \
virtual
int qt_metacall(qmetaobject::call, int, void **); \
qt是通過qobject
、qmetaobject
類實現其內省機制,
qobject
暴露給使用者的共有自省方法有objectname()
,inherits()
,iswidgettype()
等
大多數自省方法是qobject
派發給qmetaobject
實現 (e.g.qmetaobject::classname
),元物件模型編譯器moc
負責自省方法的實現
4、更多自省方法定義在qmetaobject
,是為了訊號槽通訊、事件派發等機制
QT內省機制 自定義Model 資料庫
本文將介紹自定義model過程中資料庫資料來源的獲取方法,我使用過以下三種方式獲取資料庫資料來源 本文重點介紹第二種,即利用qt的內省機制來獲取資料。1.自定義model過程 通過內省功能獲得字段值,也就是第二種方法 本文中自定義model繼承於qabstracttablemodel 重點描述set...
通過內省機制設定JavaBean
一 步驟 1 使用propertydescriptor類獲取屬性描述者物件 pd引用student的name屬性 propertydescriptor pd new propertydescriptor name student.class 2 通過getwritemethod 方法 invoke ...
01 Introspector內省機制
在j a領域程式設計中,內省機制相當的不錯,可以省去我們程式設計師很多的不必要的 比如說 在jdbc工具類 我們可以將resultset結果集待到 j abean物件中 將http請求報文的資料 轉換到乙個 j abacn物件當中去 這樣子可以省去我們很多的 request.getparameter...