C++回顾之成员函数重载、类与结构体、this指针

        前一篇文章中说到,内联成员函数的定义有两种方式,一种是在类体内部直接定义,第二种是在类体外定义。下面是代码:

        第一种定义方式:

        

class Test
{
public:
        void add(int a, int b) //类体中直接定义时为内联函数。
        {
                return a+b;
        }
};
        第二种定义方式为:

inline Test::add(int a, int b) //在类体外定义
{
        return a+b;
}
        内联函数的目的主要是为了提高程序执行的效率,编译器在编译的时候会将代码直接嵌入到调用的地方,从而减少了函数调用的开销,如果不用内联函数,直接嵌入代码,则代码体积将增大,这实际上是以空间换取时间的策略。所以内联函数的代码必须短小,内联函数对编译器而言仅仅是一个提示,另外,如果函数中含有switch for 等语句,则编译器不会将其解读为内联。
   

        下面讲讲成员函数的重载

        成员函数的重载是有条件的,首先必须具有相同的作用域,且参数不同(可以是参数类型不同,参数个数不同,参数顺序不同),函数名相同。这样的成员函数才构成重载。下面是重载的例子:

class Test
{
public:
        void Init();
        void Init(int x);
        void Init(int x, int y);
        void Init(int x, int y, int z);

        //void Init(int x=0, int y= 0, int z= 0 ); //与void Init();函数产生了二义性,编译器无法区分

};
        在上面这个例子中,定义了多个Init函数,由于他们的参数不同,所以构成重载,但是成员函数的重载需要注意的是,对于带有缺省值参数的成员函数的重载需要避免二义性,如上述代码中的注释行。它与不带参数的成员函数Init()就产生了二义性,编译器对此无法区分,因此会报错。


        类与结构体(struct 与 class)

        在C中的结构体struct其实与C++中的class有点类似的,它们都可以将各种数据结构与方法封闭在一个容器中。唯一的区别在于:在未指定访问权限时,struct默认是public的,而class默认是private的。如下:

class Test
{
    int x; //actually x is private.
};
struct Test
{
    int x; //x is public
};
        在class中可以定义函数,其实在C++中的struct内也可以定义函数,只不过他们的访问权限均为public的,如果class内定义的所有数据成员与成员函数均为public,则与struct定义没有任何区别。下面这段代码非常简单,可以看出二者的区别。

        

struct Test2
{
    int x_;
    int y_;
    int z_;

    void Init(int x, int y, int z)
    {
         x_ = x;
         y_ = y;
         z_ = z;
    }
};

class Test3
{
    int x_;
    int y_;
    int z_;

    void Init(int x, int y, int z )
    {
        x_ = x;
        y_ = y;
        z_ = z;
    }
};


int main()
{
        Test2 t; //在C++中,struct也是一个类,不需要加上struct
        t.Init(10,20,30);
        
        Test2 t2 = {10,20,30}; //C中结构体的初始化,这是允许的
         
        Test3 t3;
        t3.Init(10,20,30);//Error,Init在t3中是private的,外部无法直接访问
        
        Test3 t4 = {10,20,30}; //Error,在class中,数据成员为private,不能像struct那样初始化。

}
        

        关于this指针

        为了搞清this指针,需要了解一个背景:在C++中,成员函数的代码对所有对象而言是共享的,而每个对象的数据成员空间各自独立,那么当每个对象都调用成员函数时,成员函数如何区别它应该操作哪一个对象的数据呢?换句话说,成员函数怎么知道它要操作的是调用它的对象的数据成员?这主要是C++编译器来完成,C++编译器在每次成员函数调用时,在第一个参数会增加一个对象的指针,以告诉成员函数它要操作的是哪个对象的数据。编译器传递的这个指针是不可见的,是隐含的

我们程序代码中调用成员函数是这样的:

Test t1;
t1.Init(10,20,30);

而编译器处理后,是这样的:

Test t1;
t1.Init(&t1, 10, 20, 30);
这个被编译器传递进去的指针就是this指针了,这样在成员函数代码被执行时就指向了t1的数据成员。当然,我们在成员函数定义时可以将这个this指针省略。



C++回顾之成员函数重载、类与结构体、this指针

上一篇:C++ new和delete重载


下一篇:C++回顾之前向声明、嵌套类、局部类