您的位置:首页 > 编程语言 > C语言/C++

C++类的成员函数存储方式(是否属于类的对象)

2016-07-10 15:42 447 查看
今天在看TAF源码的时候,发现下面一段有趣的代码:

getSmallerProxyPrx =  Application::getCommunicator()->stringToProxy<GetSmallerPrx>(MobileAssist.JiangeSmallerServer.GetSmaller);

//此处T为GetSmallerPrx
template<class T> T stringToProxy(const string& objectName,const string& setName="")
{
T prx = NULL;
stringToProxy<T>(objectName, prx,setName);
return prx;
}

//此处T为GetSmallerPrx
template<class T> void stringToProxy(const string& objectName, T& proxy,const string& setName="")
{
//getServantProxy中new ServantProxy()并返回
ServantProxy * pServantProxy = getServantProxy(objectName,setName);
//将ServantProxy类型的指针强制转换为GetSmallerProxy类型的指针
//并放入GetSmallerProxy类型的智能指针中
proxy = (typename T::element_type*)(pServantProxy);
}


我们看一看这行代码:

proxy = (typename T::element_type*)(pServantProxy);


此处的proxy 的类型是T,具体来说就是GetSmallerPrx

(更具体的说,是taf::TC_AutoPtr < MobileAssist::GetSmallerProxy >)。

而pServantProxy的类型是ServantProxy *。

(typename T::element_type*)(pServantProxy)


将ServantProxy 类型的指针强制转换成GetSmallerProxy类型的指针,而ServantProxy是GetSmallerProxy的基类——我的第一反应是——这是非常危险的!比如如果GetSmallerProxy访问了某个ServantProxy没有的成员变量,将造成越界访问

不过事实上,上面的假设并不成立——GetSmallerProxy没有新的成员变量。



但是有新的成员函数——而事实是,子类特有的成员函数是可以正常访问的:



这是不是说明,类的成员函数并不占用类对象的内存空间(如果占用的话,此处的访问将越界)。

所以我做了一个简单的实验:

#include <iostream>

using namespace std;

class A
{
public:
A(){}
~A(){}
};

class B
{
public:
B(){}
virtual ~B(){}
};

class C
{
public:
C() {}
~C() {}

int add(int a, int b)
{
return a+b;
}
};

int main()
{
cout << "Size(A) = " << sizeof(A) << endl;
cout << "Size(B) = " << sizeof(B) << endl;
cout << "Size(C) = " << sizeof(C) << endl;
return 0;
}

./testClassFun
Size(A) = 1
Size(B) = 8
Size(C) = 1


结论:成员函数是不占用类对象内存空间的。

一般情况下,同一个类的不同对象,共享成员函数的代码。成员函数的代码存储在对象空间之外。换句话说,成员函数的代码,都不占据对象的存储空间。所以类的成员函数,对于类来讲,一方面是逻辑上的“属于”,一方面是物理上的“不依赖”。

所以如果成员函数未使用任何成员变量的话,不管是不是static的,都能正常工作。在调用成员函数时,将this指针传给函数以指明以哪个类对象调用。

因此,前面的类型向下转换是没问题的,并不会造成越界访问~
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: