[C++]:C++类、对象一些概念: 类成员函数、类访问修饰符、构造函数 & 析构函数、拷贝构造函数、友元函数、内联函数、this 指针、指向类的指针、静态成员

本文参考菜鸟教程

1. 类&成员

成员函数可以在类内部定义,也可以使用范围解析运算符::来定义,调用的时候使用.运算符。

//类内部定义
class Box{
	pubulic:
		double getVolume(){
		return 0.0;
		}
}
//使用::在类外部来定义
double Box::getVolume(){
	return 0.0;
}

C++中使用static关键字来把类成员定义为静态,静态成员只有一个副本,无论创建多少对象,静态成员在类中共享
可以使用范围解析运算符::来重新声明静态变量并且进行初始化。

2. 类访问修饰符

访问修饰符有public,private,protected,成员和类的默认访问修饰符是 private

class body{
	public:
	//公有成员
	private:
	//私有成员
	protected:
	//受保护成员
}
  1. 公有成员:在程序中类的外部是可访问的,可以不使用任何成员函数来设置和获取公有变量的值。
  2. 私有成员:类的外部是不可访问的且不可查看,只有类和友元函数可以访问私有成员。通过公有函数进行私有变量的设置。
  3. 受保护成员:与私有成员类似,但是保护成员在派生类(即子类)中是可访问的。
class Box{
	double height;//默认私有 不能通过box.height = 20.0 来进行设置
	protected:
		double width;
	public:
		double length;
		void setWidth(double wid);
		double getWidth();
		void setHeight(double hei);
		double getHeight();
		void setLength(double len);
		double getLength();
}
class SmallBox:Box // SmallBox 是派生类
{
   public:
      void setSmallWidth( double wid );//可以用来访问受保护成员
      double getSmallWidth( void );
};

继承同样有public,private,protected三种:

  1. public 继承:基类 public 成员,protected 成员,private 成员的访问属性在派生类中分别变成:public, protected, private
  2. protected 继承:基类 public 成员,protected 成员,private 成员的访问属性在派生类中分别变成:protected, protected, private
  3. private 继承:基类 public 成员,protected 成员,private 成员的访问属性在派生类中分别变成:private, private, private

3. 构造函数与析构函数

构造函数在每次类创建时执行。默认的构造函数没有任何参数,但如果需要,构造函数也可以带有参数。可以使用初始化列表来初始化字段。如:

Line::Line( double len): length(len)
{
    cout << "Object is being created, length = " << len << endl;
}

析构函数在每次删除类创建的对象的时候执行,析构函数的名称与类的名称是完全相同的,只是在前面加了个波浪号(~)作为前缀,它不会返回任何值,也不能带有任何参数。

4. 拷贝构造函数

拷贝构造函数是一种特殊的构造函数,它在创建对象时,是使用同一类中之前创建的对象来初始化新创建的对象。如果在类中没有定义拷贝构造函数,编译器会自行定义一个。如果类带有指针变量,并有动态内存分配,则它必须有一个拷贝构造函数。

class Line
{
   public:
      int getLength( void );
      Line( int len );             // 简单的构造函数
      Line( const Line &obj);      // 拷贝构造函数
      ~Line();                     // 析构函数
 
   private:
      int *ptr;
};
Line::Line(const Line &obj)
{
    cout << "调用拷贝构造函数并为指针 ptr 分配内存" << endl;
    ptr = new int;
    *ptr = *obj.ptr; // 拷贝值
}
 
  1. 通过使用另一个同类型的对象来初始化新创建的对象。
  2. 复制对象把它作为参数传递给函数。
  3. 复制对象,并从函数返回这个对象。
    例子:
#include <iostream>
 
using namespace std;
 
class Line
{
   public:
      int getLength( void );
      Line( int len );             // 简单的构造函数
      Line( const Line &obj);      // 拷贝构造函数
      ~Line();                     // 析构函数
 
   private:
      int *ptr;
};
 
// 成员函数定义,包括构造函数
Line::Line(int len)
{
    cout << "调用构造函数" << endl;
    // 为指针分配内存
    ptr = new int;
    *ptr = len;
}
 
Line::Line(const Line &obj)
{
    cout << "调用拷贝构造函数并为指针 ptr 分配内存" << endl;
    ptr = new int;
    *ptr = *obj.ptr; // 拷贝值
}
 
Line::~Line(void)
{
    cout << "释放内存" << endl;
    delete ptr;
}
int Line::getLength( void )
{
    return *ptr;
}
 
void display(Line obj)
{
   cout << "line 大小 : " << obj.getLength() <<endl;
}
 
// 程序的主函数
int main( )
{
   Line line1(10);
 
   Line line2 = line1; // 这里也调用了拷贝构造函数
 
   display(line1);
   display(line2);
 
   return 0;
}
/*
调用构造函数
调用拷贝构造函数并为指针 ptr 分配内存
调用拷贝构造函数并为指针 ptr 分配内存
line 大小 : 10
释放内存
调用拷贝构造函数并为指针 ptr 分配内存
line 大小 : 10
释放内存
释放内存
释放内存
*/

5. 友元函数

类的友元函数是定义在类外部,但有权访问类的所有私有(private)成员和保护(protected)成员。尽管友元函数的原型有在类的定义中出现过,但是友元函数并不是成员函数。
如果要声明函数为一个类的友元,需要在类定义中该函数原型前使用关键字 friend

class Box
{
   double width;
public:
   double length;
   friend void printWidth( Box box );
   void setWidth( double wid );
};

声明类 ClassTwo 的所有成员函数作为类 ClassOne 的友元,需要在类 ClassOne 的定义中放置如下声明:

friend class ClassTwo;

6. 内联函数

如果一个函数是内联的,那么在编译时,编译器会把该函数的代码副本放置在每个调用该函数的地方。如果想把一个函数定义为内联函数,则需要在函数名前面放置关键字 inline,在调用函数之前需要对函数进行定义。如果已定义的函数多于一行,编译器会忽略 inline 限定符。

7. this 指针

在 C++ 中,每一个对象都能通过 this 指针来访问自己的地址。this 指针是所有成员函数的隐含参数。因此,在成员函数内部,它可以用来指向调用对象。
友元函数没有 this 指针,因为友元不是类的成员。只有成员函数才有 this 指针。

Box* get_address()   //得到this的地址
{
	return this;
}

指向类的指针

一个指向 C++ 类的指针与指向结构的指针类似,访问指向类的指针的成员,需要使用成员访问运算符->,就像访问指向结构的指针一样。与所有的指针一样,您必须在使用指针之前,对指针进行初始化。

类的静态成员

  1. 静态成员
    使用 static 关键字来把类成员定义为静态的。当我们声明类的成员为静态时,这意味着无论创建多少个类的对象,静态成员都只有一个副本。
    静态成员在类的所有对象中是共享的。如果不存在其他的初始化语句,在创建第一个对象时,所有的静态数据都会被初始化为零。我们不能把静态成员的初始化放置在类的定义中,但是可以在类的外部通过使用范围解析运算符 :: 来重新声明静态变量从而对它进行初始化,如下面的实例所示。
class Box
{
   public:
      static int objectCount;
}
int Box::objectCount = 0;
  1. 静态成员函数
    如果把函数成员声明为静态的,就可以把函数与类的任何特定对象独立开来。静态成员函数即使在类对象不存在的情况下也能被调用,静态函数只要使用类名加范围解析运算符 :: 就可以访问。
    静态成员函数只能访问静态成员数据、其他静态成员函数和类外部的其他函数。
    静态成员函数有一个类范围,他们不能访问类的 this 指针。您可以使用静态成员函数来判断类的某些对象是否已被创建。

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

  • 静态成员函数没有 this 指针,只能访问静态成员(包括静态成员变量和静态成员函数)。
  • 普通成员函数有 this 指针,可以访问类中的任意成员;而静态成员函数没有 this 指针。
#include <iostream>
 
using namespace std;
 
class Box
{
   public:
      static int objectCount;
      // 构造函数定义
      Box(double l=2.0, double b=2.0, double h=2.0)
      {
         cout <<"Constructor called." << endl;
         length = l;
         breadth = b;
         height = h;
         // 每次创建对象时增加 1
         objectCount++;
      }
      double Volume()
      {
         return length * breadth * height;
      }
      static int getCount()
      {
         return objectCount;
      }
   private:
      double length;     // 长度
      double breadth;    // 宽度
      double height;     // 高度
};
 
// 初始化类 Box 的静态成员
int Box::objectCount = 0;
 
int main(void)
{
  
   // 在创建对象之前输出对象的总数
   cout << "Inital Stage Count: " << Box::getCount() << endl;
 
   Box Box1(3.3, 1.2, 1.5);    // 声明 box1
   Box Box2(8.5, 6.0, 2.0);    // 声明 box2
 
   // 在创建对象之后输出对象的总数
   cout << "Final Stage Count: " << Box::getCount() << endl;
 
   return 0;
}
/*
Inital Stage Count: 0
Constructor called.
Constructor called.
Final Stage Count: 2
*/
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值