wow7jiao 发表于 2020-1-18 20:14:22

C++静态成员问题

本帖最后由 wow7jiao 于 2020-1-18 20:19 编辑

<

class A {
public:
A(int a=0){x=a;}
static void f1(){};
private:
int x;
static int y;
};
int main(){
A::y = 0;
A::f1();
return 0;
}

>

上面的代码编译时会出现错误。请问哪里错了。

下面是这个章节的介绍

Instance Members and Static Members
实例成员与静态成员




1. Declaration and Definition of Static Members (声明或定义静态成员)


1.1. 静态成员的声明


Inside a class definition, "static" declares members that are not bound to class instances
在类定义中,关键字 static 声明 不绑定到类实例的成员( 该成员无需创建对象即可访问)



1.2. 静态数据成员的定义


静态数据成员定义的规则



(1)声明为“constexpr”类型的静态数据成员必须 在类中声明 并初始化。自C++17 起,可不在类外定义

(2)声明为“inline”(C++17 起) 或者 “const int”类型的静态数据成员可以 在类中声明 并初始化;

(3)其它须在类外 定义并初始化,且不带static 关键字



静态数据成员的定义规则复杂,在类外定义,大部分情况下不会出错



详细的使用方法参见:https://en.cppreference.com/w/cpp/language/static





2. Static member (静态成员)


2.1. 静态数据成员具有静态存储期(static storage duration)或者C++11线程存储期特性


2.2. 静态存储期


The storage for the object is allocated when the program begins and deallocated when the program ends. ( 对象的存储在程序开始时分配,而在程序结束时解回收)



(1)      Only one instance of the object exists ( 只存在对象的一个实例)

(2)      静态存储器对象未明确初始化时会被自动“零初始化(Zero-Initialization)”







3. Instance Members and Static Members (实例成员和静态成员)


在下面的例子中,一旦实例化了Square(创建了Square的对象),每个对象中都有各自的side成员。这个side成员就叫做实例成员。



而numberOfObjects只存在一个,是由所有的Square对象共享的,叫做静态成员。



class Square {

private:

double side;

static int numberOfObjects;

// ...

public:

Square():Square(1.0){

}

Square(double side){

    this->side = side;

    numberOfObjects++;

}

// ...

};

int Square::numberOfObjects;

int main() {

    Square s1{}, s2{5.0};

}



下面的图中,展示了实例成员和静态成员的不同。








>

Croper 发表于 2020-1-18 20:14:23

2楼说得对啊,另外:

我放在vs里面,提示是第12行的问题,找不到A::y
你的y是在private里的,main访问不了。

还有你报错的信息是什么

编程难 发表于 2020-1-18 20:33:04

类静态成员需要显示实例化一下。
在类外部写一句
int A::y = 1;

wow7jiao 发表于 2020-1-18 20:34:18

编程难 发表于 2020-1-18 20:33
类静态成员需要显示实例化一下。
在类外部写一句
int A::y = 1;

类可以自动实例化为0,我加int错误更多了。

wow7jiao 发表于 2020-1-18 20:39:35

wow7jiao 发表于 2020-1-18 20:34
类可以自动实例化为0,我加int错误更多了。

我放在vs里面,提示是第12行的问题,找不到A::y

wow7jiao 发表于 2020-1-18 20:55:56

Croper 发表于 2020-1-18 20:47
2楼说得对啊,另外:




类里面的静态成员是不需要实例化的可以直接调用,在类外初始化。

wow7jiao 发表于 2020-1-18 20:59:59

本帖最后由 wow7jiao 于 2020-1-18 21:09 编辑

上面的截图,这个题的章节是讲类的静态成员,重点是初始化要在类外,“(3)其它须在类外 定义并初始化,且不带static 关键字”,这个题是第五题,有点难度,和课件讲解我是没看出有什么不一样。

Croper 发表于 2020-1-18 21:13:14

wow7jiao 发表于 2020-1-18 20:59
上面的截图,这个题的章节是讲类的静态成员,重点是初始化要在类外,“(3)其它须在类外 定义并初始化,且 ...

定义在main外面class A {
public:
        A(int a = 0) { x = a; }
        static void f1() {};
        static int y;
private:
        int x;
};
int A::y = 0;

wow7jiao 发表于 2020-1-18 21:15:21

我刚才试了一下放在Main()外面可以,这个细节太奇怪了。

Croper 发表于 2020-1-18 21:21:49

wow7jiao 发表于 2020-1-18 21:15
我刚才试了一下放在Main()外面可以,这个细节太奇怪了。

类里的只是个声明,和extern int A没多大区别。
类在完全编译后是一堆函数,存储在代码区,而静态变量是要放在全局常量区的。这两个东西当然要分开写了

wow7jiao 发表于 2020-1-18 21:22:58

Croper 发表于 2020-1-18 21:13
定义在main外面

数据还是要放在private里面,不然安全性太差了。

Croper 发表于 2020-1-18 21:51:56

wow7jiao 发表于 2020-1-18 21:22
数据还是要放在private里面,不然安全性太差了。

我看你的格式还以为你要在main里面调用
页: [1]
查看完整版本: C++静态成员问题