内联函数

1
2
3
4
inline 返回类型  类名::成员函数名(参数表)
{
// 函数体
}

注意:在类内声明时不用inline

注意:使用inline说明内联函数时,必须使函数体和inline说明结合在一起,否则编译器将它作为普通函数处理。

例:

1
inline  void Coord:: setCoord(int ,int);

不能说明这是一个内联函数。

指向类的成员的指针

  • 指向成员的指针只能访问公有数据成员和成员函数。

  • 使用要先声明,再赋值,然后访问。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    声明:类型说明符 类名:: *数据成员指针名;
    //例如:
    int A∷*pc2;
    赋值:数据成员指针名=&类名:: 数据成员名
    //例如:
    pc2=&A∷z; // 给数据成员指针pc2赋值 //

    使用:对象名. *数据成员指针名
    对象指针名-> *数据成员指针名

指向成员函数的指针

1
2
3
4
5
6
7
声明:类型说明符  (类名∷ *指针名)(参数表); 
赋值:成员函数指针名 = 类名∷成员函数名; 
使用:(对象名.*成员函数指针名)(参数表)  ;
(对象指针名 -> *成员函数指针名)(参数表) ;
//例如:
int (Coord∷*pc_getx)();
pc_getx=Coord∷getx;

静态成员

静态数据成员用关键字static声明,该类的所有对象维护该成员的同一个拷贝,必须在类外定义和初始化,用(::)来指明所属的类。

在类的声明中只能声明静态数据成员的存在。由于类的声明是抽象的,静态数据成员的初始化需要在类的外部进行,通过类名对它进行访问。

静态数据成员初始化的格式如下:

1
<数据类型><类名>∷<静态数据成员名>=<值>;

初始化时不加该成员的访问权限控制符private,public等。

引用静态数据成员时,采用如下格式:(只能访问公有静态数据成员)

1
2
3
可用类名访问:  类名::静态数据成员
也可用对象访问: 对象名.静态数据成员
对象指针->静态数据成员

静态成员函数可以直接访问该类的静态数据成员和函数成员;而访问非静态数据成员,必须通过参数传递方式得到对象名,然后通过对象名来访问。

定义静态成员函数的格式如下:

1
static 返回类型 静态成员函数名(参数表);

使用目的:在对象建立之前处理静态数据成员或全局变量,与静态数据成员类似, 使用公有静态成员函数的一般格式有如下几种:

1
2
3
类名::静态成员函数名(实参表)
对象. 静态成员函数名(实参表)
对象指针->静态成员函数名(实参表)
  • 静态成员函数可以定义成内嵌的,也可以在类外定义,在类外定义时不能用static前缀。
  • 使用静态成员函数的一个原因是,可以用它在建立任何对象之前处理静态数据成员。这是普通成员函数不能实现的。
  • 静态成员函数中没有指针this,所以静态成员函数不访问类中的非静态数据成员,若确实需要则只能通过对象名(作为参数)访问。

通过指针可以访问类的静态成员或静态成员函数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
#include<iostream.h>
class myclass {
public:
myclass() // 构造函数,每定义一个对象,
{ ++i; } // 静态数据成员i加1
static int i; // 声明静态数据成员i
};
int myclass::i=0; // 静态数据成员i初始化,
//不必在前面加static
main()
{ int *count=&myclass::i;
myclass ob1,ob2,ob3,ob4;
cout<<“ myclass::i= ”<<*count<<endl;
return 0; }
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include<iostream.h>
class myclass {
public:
myclass()
{ ++i; }
static int geti()
{ return i; }
private:
static int i;
};
int myclass::i=0;
main()
{ int (*get)()=myclass::geti;
myclass ob1,ob2,ob3;
cout<<"myclass∷i="<<(*get)()<<endl;
return 0;
}

友元

  • 友元函数的声明:
    位置:当前类体中.
    格式:函数名前加friend
  • 友元函数的定义:
    类体外:同一般函数(函数名前不能加 类名::)
    类体内:函数名前加friend
  • 友元函数没有this指针,它通过入口参数(该类对象)来访问对象的成员
  • 注意友元函数常常伴随着提前引用问题
  • 关于友元类
    • 友元关系是单向的,不具有交换性
      即若类X是类Y的友元,但类Y不一定是类X的友元。
    • 友元关系不具有传递性
      即若类X是类Y的友元,类Y是类Z的友元,但类X不一定是类Z的友元。

对象成员

关键问题是对象成员的初始化,也就是构造函数如何设计的问题

1
2
3
4
5
X::X(形参表0):对象成员名1(形参表1),…,
对象成员名i(形参表i) ,…,对象成员名n(形参表n)
{
// …构造函数体
}

例如:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
#include<iostream.h>
class A{
public:
A(int x1,float y1)
{ x=x1; y=y1; }
void show()
{ cout<<"\n x="<<x<<" y="<<y; }
private:
int x;
float y;
};
class B{
public:
B(int x1,float y1,int z1):a(x1,y1)
{ z=z1; }
void show()
{ a.show();
cout<<" z="<<z; }
private:
A a;
int z;
};
main()
{ B b(11,22,33);
b.show();
return 0;
}

具有对象成员的类的构造函数的另一种形式如下:

1
2
3
4
5
6
7
8
B(A a1,int z1):a(a1)
{ z=z1; }
main()
{ A a(11,22);
B b(a,33);
b.show();
return 0;
}

这时析构函数不需要析构其对象成员。