讲一点Python类成员和C++类成员的构造区别

电子说

1.3w人已加入

描述

>>> 背景

如果同时写两种类型语言的代码,难免有的时候会产生一点混淆,这也正是思维碰撞的时候。今天来讲一点Python类成员和C++类成员的构造区别。在C++里面,就要求把类成员显式地声明出来,这样才能够在构造函数里面对成员进行初始化,就如下所示。

class A
{
public:
    int n_;
    A(int n) : n_(n){}
};

如果使用python定义类的话,类成员的定义和初始化都放在了构造函数里面,少了那么一点仪式感,就如下面所示。

class Dog:
    def __init__(self, m):
        self.m_ = m

这个时候如果硬是要为python类先声明一个成员,从语法上也是可以的,如下所示。

class Dog:
    n_ = 0
    def __init__(self, n):
        self.n_ = n

这就引出了今天的问题,在python中像 n_ = **0 **这样的语句,到底是什么含义呢?

>>> 解释

其实在上述代码中,为classDog创造了一个类静态成员,该静态成员为类所有的数据。而 self .m_ = m 才是为类的实例所有的数据。通过类静态成员,可以管理一些实例无关的数据,比如某个数学类中的圆周率、已经创建的实例的个数等等。

如下面就通过 count** *** 这个类静态成员,统计了实例化的次数;注意这里使用了 Dog.count*** ** 来访问类静态成员,而不是 self.count**_**。


class Dog:
    count_ = 0
    def __init__(self, n):
        self.n_ = n
        Dog.count_ += 1


if __name__ == '__main__':
    for i in range(3):
        g = Dog(2 * i)
        print(Dog.count_, " n: ", g.n_)
 >>
1  n:  0
2  n:  2
3  n:  4

相比而言,C++创建类静态成员的方法如下所示。使用关键字 static 来声明一个静态成员。对于非const类型的类静态成员,C++还要求在类外部进行初始化,如int Dog::count = 0 ; 。

注意下面这种统计构造次数的方法仅仅是统计了普通构造,并没有统计默认构造、拷贝构造或者赋值构造。通过析构函数可以看到,随着对象的过期,对象的个数也逐渐减少到归0了。

class Dog
{
public:
    static int count;
    int n_;
    Dog(int n): n_(n) { count++; }
    ~Dog() { count--; }
};


int Dog::count = 0;


int main()
{
    {
        Dog g1(0);
        cout < < Dog::count < < " n: " < < g1.n_ < < endl;
        Dog g2(2);
        cout < < Dog::count < < " n: " < < g2.n_ < < endl;
        Dog g3(4);
        cout < < Dog::count < < " n: " < < g3.n_ < < endl;
    }
    cout < < Dog::count < < endl;
}
 >>
1 n: 0
2 n: 2
3 n: 4
0
打开APP阅读更多精彩内容
声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉

全部0条评论

快来发表一下你的评论吧 !

×
20
完善资料,
赚取积分