C++——静态成员与this指针

一、静态成员

1.1静态数据成员

被类的实例共享,而不是某个特定类对象
静态数据成员的作用域和初始化
用关键字 static 声明

  • 可以被声明为 public, private, protected
  • 当声明类的数据成员为静态时,无论创建多少个类的对象,静态成员都只有一个副本
  • 在类的所有对象中共享,具有静态生存期
  • 基本数据类型的的静态数据成员默认情况初始化为零
  • 类内声明,类外定义和初始化并用范围解析运算符(::)指明所属的类。int, enum 类型的 const static 数据成员可以在类定义中声明时初始化
  • 具有默认构造函数的类类型的静态数据成员(即静态成员对象)不必初始化,其默认构造函数会被调用

访问静态数据成员
通常通过类的静态成员函数或类的友元访问类的 private, protected 静态成员
当类没有对象时

  • 要访问 public 静态数据成员,需在成员名前加类名和二元作用域运算符(::)
  • 要访问 private, protected 静态数据成员,需提供 public 静态成员函数,并通过在函数名前加类名和二元作用域运算符(::)调用函数

1.2静态成员函数

把成员函数声明为静态的,就可以把函数与类的任何特定对象独立开来

  • 在类对象不存在的情况下也能被调用,使用类名加范围解析运算符 :: 即可访问
  • 静态成员函数只能访问静态成员数据、其他静态成员函数和类外部的其他函数
  • 静态成员函数有一个类范围,不能访问类的 this 指针,可以使用静态成员函数来判断类的某些对象是否已被创建
  • 用静态成员函数访问非静态成员,需通过对象
#include <iostream>
using namespace std;
 
class Box {
public:
    static int count;    //若该静态数据成员在private部分声明,则只能通过静态成员函数处理
    Box(double l, double b, double h);
    double Volume();
    static int getCount();
private:
    double length, width, height;
};
 
int Box::count = 0;
Box::Box(double l = 2.0, double b = 2.0, double h = 2.0) {
    cout <<"One constructor was called." << endl;
    length = l, width = b, height = h;
    count++;
}
double Box::Volume() {
    return length * width * height;
}
int Box::getCount() {   //静态成员函数 
    return count;
}
 
int main(void) {
    //在创建对象之前输出对象的总数
    cout << "Inital Stage Count: " << Box::getCount() << endl;
    
    Box Box1(3.3, 1.2, 1.5);
    Box Box2(8.5, 6.0, 2.0);
    
    //在创建对象之后输出对象的总数
    cout << "Final Stage Count: " << Box::getCount() << endl;
    return 0;
}
 
结果:
Inital Stage Count: 0
One constructor was called.
One constructor was called.
Final Stage Count: 2 

注:
静态成员函数与普通成员函数的区别

  • 静态成员函数没有 this 指针,只能访问静态成员(包括静态成员变量和静态成员函数)
  • 普通成员函数有 this 指针,可以访问类中的任意成员;而静态成员函数没有 this 指针

使用静态成员了解构造与析构函数的调用情况

#include <iostream>
using namespace std;
 
class Cpoint {
public:
    static int value;
    static int num;
    Cpoint(int x,int y) {
        xp = x, yp = y;
        value++;
        cout << "调用构造:" << value << endl;
    }
    ~Cpoint() { num++; cout << "调用析构:" << num << endl; }
private:
    int xp, yp;
};
class CRect {
public:
    CRect(int x1,int x2) : mpt1(x1,x2), mpt2(x1,x2) { cout << "调用构造\n"; }
    ~CRect() { cout << "调用析构\n"; }
private:
    Cpoint mpt1, mpt2;
};
int Cpoint::value=0;
int Cpoint::num=0;
 
int main() {
    CRect p(10,20);
    cout << "Hello, world!" << endl;
    return 0;
}
 
结果:
调用构造:1
调用构造:2
调用构造
Hello, world!
调用析构
调用析构:1
调用析构:2 

二、this指针

每个对象可通过一个称为 this 的指针访问自己的地址

  • 对象的指针不是对象本身的一部分,即 this 所占的内存不会在对对象进行 sizeof 操作的结果中体现
  • this 指针作为隐式的实参传递给对象的各个非 static 成员函数
  • static 成员函数没有 this 指针,因为 static 数据成员和 static 成员函数独立于类的任何对象而存在,而 this 指针必须指向特定的类对象
  • this 指针的类型取决于对象的类型和使用 this 指针的成员函数是否声明为 const
  • this 指针可以防止对象赋值给自己
#include<iostream>
using namespace std;
 
class Test {
public:
    Test(int = 0);
    void print();
private:
    int x;
};
 
Test::Test(int value) : x(value) { }
void Test::print() {
    cout << "\tx = " << x
    << "\nthis -> x = " << this -> x
    << "\n(*this).x = " << (*this).x << endl;
}
 
int main() {
    Test test(20);
    test.print();
    return 0;
}
 
结果:
        x = 20
this -> x = 20
(*this).x = 20

转载于:https://www.cnblogs.com/xxwang1018/p/11546664.html

  • 7
    点赞
  • 15
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值