社区应用 最新帖子 精华区 社区服务 会员列表 统计排行 社区论坛任务 迷你宠物
  • 5464阅读
  • 3回复

[C/C++]一个简易的类型判别器

发帖
7
铜板
13
人品值
61
贡献值
2
交易币
0
好评度
7
信誉值
0
金币
0
所在楼道
                                一个简易的类型判别器 EqD@o  
             %CQa8<q  
                        在某些时候,我们需要判别一个对象的类型,C++提供了RTTI(运行时类型信息)机制,比如使用 typeid 关键字,但 Bjarne 建议尽量不要使用RTTI来判定对象类别,他提倡多使用使用 dynamic_cast 替代 typeid。当然typyid能准确判定对象的类型,而dynamic_cast不一定总能告诉我们对象的确切类型。 E 8W*^^z(  
SLkgIb~'X  
下面是一个简单的类型判别器(不能用于基本类型,如int、double等): bSI*`Dc"!  
代码: 全选/* G DBV  
* File: TypeUtils.h e]!`94f  
* Author: kwarph [ kwarph@gmail.com ] s]=XAm"4  
* Time: 2009-3-21 下午03:25:02 ixM#|Yq  
* ?^-fivzS>  
* Copyright (C) 2008-2009, kwarph, All Rights Reserved. h^IizrqU  
*/ Qt'3v"S>)  
2HE<WI^#h  
#ifndef TYPEUTILS_H_ Xeis_  
#define TYPEUTILS_H_ [=. iJ5,{2  
T[[E)f1[  
template<typename T> FR50y+h^$  
struct InstanceOf { 9P <1/W!  
\N?lG q  
    template<typename T1> %ByqkY{5F  
    static bool test(const T1*& ptr) { DD7D&@As  
        const T* t = dynamic_cast<const T*> (ptr); UDk H'x$=  
        return t != 0; +('xzW  
    } Xsb.xxK.  
s;Zi   
    template<typename T1>  56C'<#  
    static bool test(T1*& ptr) { Gyi0SM6v5&  
        T* t = dynamic_cast<T*> (ptr); &kWT<*;J)  
        return t != 0; M9VAs~&S  
    } FDBNKQV  
.gRb'  
    template<typename T1> h>xB"E|.  
    static const T* get(const T1*& ptr) { z:O:g?A  
        const T* t = dynamic_cast<const T*> (ptr); b4KNIP7E  
        return t; 9ygNJX'~  
    } /NPx9cLW^  
fWg 3gRI  
    template<typename T1> 7S= ]@*  
    static T*& get(T1*& ptr) { vsA/iH.  
        return dynamic_cast<T*> (ptr); Q}lY1LT`  
    } d"ZsOq10D  
}; ,HE{&p2y  
0Iyb}  
#endif /* TYPEUTILS_H_ */             '|tmmoY6a:  
<[gN4x>'  
Q  Q: 570508473 8&x&Ou$("V  
邮  件:athzhang@gmail.com /^~)iTwH  
电  话:(0512) 55253348,(0) 18912671348 y(C',Xn  
地  址:江苏省 昆山市 前进西路1088号虹桥大厦 2单元 6楼 \dB z-H'@  
评价一下你浏览此帖子的感受

精彩

感动

搞笑

开心

愤怒

无聊

灌水
发帖
7
铜板
13
人品值
61
贡献值
2
交易币
0
好评度
7
信誉值
0
金币
0
所在楼道
只看该作者 1 发表于: 2009-08-04
Re: 一个简易的类型判别器 ~-yq,x  
z+_d*\  
[w  FK!?  
下面作一个简单的测试,假设有一组对象,其继承关系如下: _lH:%E*  
JsX}PVuL  
animal.png (c3O> *M  
    animal.png (8.28 KiB) 被浏览 187 次 ,k:>Z&:  
D#>d+X$  
-Y"2c,~pH  
gazX2P[D  
我们可以这么使用 InstanceOf类: FYg{IKg  
77]Fp(uI  
代码: 全选 6%c]{eTd9  
    Animal* a1 = new Lion; VB+_ kR6Zv  
    Animal* a2 = new Swallow; ?%>S5,f_  
o8A(Cg}  
    // 1,判断 a1 是不是鸟类: /dR:\ffz2  
    bool isBird = InstanceOf<Bird*>::test(a1); // isBird为false,a1是狮子 K[-G2  
)4GCL(&  
    // 2,判断 a1 是不是狮子: QcdAg%"yy  
    bool isLion = InstanceOf<Lion*>::test(a1); .g_Kab3?L  
_^0UK|[  
    // 3,判断 a2 是不是鸟类: y&F&Z3t  
    isBird = InstanceOf<Bird*>::test(a1); // isBird为true,a2 是燕子,所以是鸟类 *@ S+J$  
2) Q/cH\g  
@Rqn&tA8  
=#I/x=L:  
在 3,判断 a2 是不是鸟类 的判断中,typeid无法达到我们所要的效果,因为: KW36nY\7  
ph7]*W-  
代码: 全选 a0wpsl iF  
    isBird = (typeid(*a2) == typeid(Bird)); // isBird 为 false vWYU'_=  
^{O1+7d[.  
_6sSS\  
V$  MMK  
typeid()返回的是对象实际的类型,也就是说Swallow虽然是Bird,但这是两个不同的类型。 Ez^wK~  
Q"GZh.m  
Q  Q: 570508473  ML1/1GK*i+  
邮  件:]athzhang@gmail.com R8, g^N  
电  话:(0512) 55253348,(0) 18912671348 cEPqcy *  
地  址:江苏省 昆山市 前进西路1088号虹桥大厦 2单元 6楼 )
发帖
7
铜板
13
人品值
61
贡献值
2
交易币
0
好评度
7
信誉值
0
金币
0
所在楼道
只看该作者 2 发表于: 2009-08-04
Re: 一个简易的类型判别器 @ql S #(  
lM%3 ?~?Q&  
KN\tRE  
其实很多场合用得上的,比如我们目前进行的CAD项目,在前台的界面的绘图区中选取一批对象,其中也许有Line、Conic、BezierCurve、 BSplineCurve等,但都属于Curve,我们可以对它们的共有特性进行统一修改(比如在对话框1中列举公共的特性,即Curve的属性),但如果我们选择的是一条直线,那么我们必须确定这个被选择的对象就是Line,弹出合适的对话框(罗列Line对象的可修改的属性),这个时候,我们可以用上面的InstanceOf。 T5TA kEVl  
+78cQqDY!  
当然,好的设计总能减少对类型确认的需要,但我想应该不能完全避免吧。 =i Wn T  
wvEdZGO8!  
昆山轩辕高端IT培训中心 OGnuBK  
Q  Q: 570508473 %Wg8dy|  
邮  件:athzhang@gmail.com V.kf@  
电  话:(0512) 55253348,(0) 18912671348 1n>(CwLG"  
地  址:江苏省 昆山市 前进西路1088号虹桥大厦 2单元 6楼
发帖
7
铜板
13
人品值
61
贡献值
2
交易币
0
好评度
7
信誉值
0
金币
0
所在楼道
只看该作者 3 发表于: 2009-08-05
Q  Q: 570508473 u_%L~1+'  
主页:http://www.xuanyuan-soft.cn [Pz['q L3t  
论坛:http://www.xuanyuan-soft.cn/forums
描述
快速回复

您目前还是游客,请 登录注册
温馨提示:欢迎交流讨论,请勿纯表情、纯引用!
认证码:
验证问题:
3+5=?,请输入中文答案:八 正确答案:八