广州C/C++培训
达内广州岗顶中心

18087159764

热门课程

C++类(Class)总结(一)详细介绍

  • 时间:2015-10-28
  • 发布:danei
  • 来源:danei

1
C++类的定义
关于类定义的一些基础知识就不一一列出了,这里会列出一些细节知识点以及需注意的知识点。
1.类成员
类可以没有成员,也可以定义多个成员。成员可以是数据、函数或类型别名。所有的成员都必须在类的内部声明。
注:没有成员的类是空类,空类也占用空间。
class People
{
};
sizeof(People) = 1;
2.内联函数
有三种:
(1)直接在类内部定义。
(2)在类内部声明,加上inline关键字,在类外部定义。
(3)在类内部声明,在类外部定义,同时加上inline关键字。
注意:此种情况下,内联函数的定义通常应该放在类定义的同一头文件中,而不是在源文件中。这是为了保证内联函数的定义在调用该函数的每个源文件中是可见的。
3.类声明
class Screen;
在声明之后,定义之前,只知道Screen是一个类名,但不知道包含哪些成员。只能以有限方式使用它,不能定义该类型的对象,只能用于定义指向该类型的指针或引用,声明(不是定义)使用该类型作为形参类型或返回类型的函数。
void Test1(Screen& a){};
void Test1(Screen* a){};
4.类定义
在创建类的对象之前,必须完整的定义该类,而不只是声明类。所以,类不能具有自身类型的数据成员,但可以包含指向本类的指针或引用。
class LinkScreen
{
public:
Screen window;
LinkScreen* next;
LinkScreen* prev;

};
 //注意,分号不能丢
因为在类定义之后可以接一个对象定义列表,可类比内置类型,定义必须以分号结束:
class LinkScreen{ /* ... */ };
class LinkScreen{ /* ... */ } scr1,scr2;
5.何时使用this指针
当我们需要将一个对象作为整体引用而不是引用对象的一个成员时。最常见的情况是在这样的函数中使用 this:该函数返回对调用该函数的对象的引用。
class Screen
{
...
public:
Screen& set(char);
};
Screen& Screen::set(char c)
{
contents[cursor] = c;
return *this;
}
6.类作用域
注意:成员函数的返回类型不一定在类作用域中。可通过 类名::来判断是否是类的作用域,::之前不属于类的作用域,::之后属于类的作用域。例如
Screen:: 之前的返回类型就不在类的作用域,Screen:: 之后的函数名开始到函数体都是类的作用域。
class Screen
{
public:
typedef std::string::size_type index;
index get_cursor() const;
};
Screen::index Screen::get_cursor() const //注意:index前面的Screen不能少
{
return cursor;
}
该函数的返回类型是 index,这是在 Screen 类内部定义的一个类型名。在类作用域之外使用,必须用完全限定的类型名 Screen::index 来指定所需要的 index 是在类 Screen 中定义的名字。
请输入正文
2
构造函数
1.构造函数可以重载
可以为一个类声明的构造函数的数量没有限制,只要每个构造函数的形参表是唯一的。
class Sales_item;
{
public:
Sales_item(const std::string&);
Sales_item(std::istream&);
Sales_item(); //默认构造函数
};
2.构造函数初始化式
与其他函数一样,构造函数具有名字、形参表和函数体。
与其他函数不同的是,构造函数可以包含一个构造函数初始化列表
Sales_item::Sales_item(const string &book): isbn(book), units_sold(0), revenue(0.0){ }
构造函数初始化列表以一个冒号开始,接着是一个以逗号分隔的数据成员列表,每个数据成员后面跟一个放在圆括号中的初始化式。
构造函数可以定义在类的内部或外部。构造函数初始化只在构造函数的定义中指定。
构造函数分两个阶段执行:(1)初始化阶段;(2)普通的计算阶段。初始化列表属于初始化阶段(1),构造函数函数体中的所有语句属于计算阶段(2)。
初始化列表比构造函数体先执行。不管成员是否在构造函数初始化列表中显式初始化,类类型的数据成员总是在初始化阶段初始化。
3.哪种类需要初始化式
const 对象或引用类型的对象,可以初始化,但不能对它们赋值,而且在开始执行构造函数的函数体之前要完成初始化。
初始化 const 或引用类型数据成员唯一机会构造函数初始化列表中,在构造函数函数体中对它们赋值不起作用
没有默认构造函数的类类型的成员,以及 const 或引用类型的成员,必须在初始化列表中完成初始化。
class ConstRef
{
public:
ConstRef(int ii);
private:
int i;
const int ci;
int &ri;
};
ConstRef::ConstRef(int ii)
{
i = ii; // ok
ci = ii; // error
ri = i; //
}
应该这么初始化:
ConstRef::ConstRef(int ii): i(ii), ci(i), ri(ii) { }
注意:成员被初始化的次序就是定义成员的次序,跟初始化列表中的顺序无关。
4.默认构造函数
不含形参的构造函数就是默认构造函数。
只要定义一个对象时没有提供初始化式,就使用默认构造函数。如: A a;
为所有形参提供默认实参的构造函数也定义了默认构造函数。例如:
class A
{
public:
A(int a=1,char c =''){}
private:
int ia;
char c1;
};
5.隐式类类型转换
1.只含单个形参的构造函数能够实现从形参类型到该类类型的一个隐式转换
class A
{
public:
A(int a)
{
ia =a;
}
bool EqualTo(const A& a)
{
return ia == a.ia;
}
private:
int ia;
};
A a(1);
bool bEq = false;
bEq = a.EqualTo(1);//参数为1,实现从int型到A的隐式转换
2.抑制由构造函数定义的隐式转换
通过将构造函数声明为 explicit,来防止在需要隐式转换的上下文中使用构造函数: 
class A
{
public:
explicit A(int a )
{
ia =a;
}
bool EqualTo(const A& a)
{
return ia == a.ia;
}
private:
int ia;
};
通常,除非有明显的理由想要定义隐式转换,否则,单形参构造函数应该为 explicit。将构造函数设置为 explicit 可以避免错误。

转载自:小熊之家 作者:小熊Kevin
上一篇:C++的另一种错误处理策略方法
下一篇:C、C在10月TIOBE排行榜:依然稳居前三

C++语言编程的学习

C语言和C++区别 你知道多少

C/C++/JAVA那个更好的作为入门语言

C++语言的15个晦涩特性 由浅入深

选择城市和中心
贵州省

广西省

海南省

台湾