提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档
文章目录
# 前言
一、作用域
1.函数原型作用域
函数声明式形参作用范围就是函数原型作用域在()范围。
2.局部作用域
在花括号定义范围之内
{
}
3.类作用域
4.命名空间作用域
为了避免出现命名危机,两个项目组在完成一个项目时使用了相同的名称。
namespace{
}
具有命名空间作用域的变量也称为全局变量。
5.特殊命名空间
(1)匿名命名空间,只能在本文件使用。
namespace
{
}
(2)全局命名空间
void bar()
{
}
main
{
//全局命名空间作用域
::bar();
}
二、生存周期
匿名对象:生存期就在一行。
所有的匿名对象都是右值。
可以用常常引用,将匿名对象变成一个左值。
在加完const之后匿名的对象的生存周期,到程序执行结束。
int (1)
const &ret = int (1);
三、类的静态成员
静态数据成员:
类的静态成员只有一份内存空间,是类成员所共有的一种属性。
访问方式:
(1)如果有对象,可以通过对象名打点访问。
(2)没有对象,可以通过类名::+静态数据成员形式访问。(习惯上这种范围方式就是代表该属性为静态)
(3)静态数据成员,在全局区,sizeof计算时不计算静态数据成员。
静态成员函数:
函数名前加static,可以通过类名::+函数名形式访问。
注意:
静态成员函数没有THIS指针。
在类的静态成员函数中不能访问非静态成员函数。
在非静态函数中可以使用静态函数,或者静态数据成员。
四、单例模式
一共有23种设计模式。
1.懒汉模式
动态加载,调用函数创建对象。
class Sigleton
{
public:
static Sigleton *creat()
{
if(m_p == NULL)
{
m_p = new Sigleton;
count++;
}
return m_p;
}
static void destroy()
{
delete m_p;
m_p = NULL;
count--;
}
static int showCount()
{
return count;
}
private:
Sigleton(){}
Sigleton(const Sigleton &){}
static Sigleton *m_p;
static int count;
};
2.饿汉模式
静态加载,主程序运行之前,创建对象。
class Sigleton
{
public:
static Sigleton *creat()
{
if(m_p == NULL)
{
m_p = new Sigleton;
count++;
}
return m_p;
}
static void destroy()
{
delete m_p;
m_p = NULL;
count--;
}
static int showCount()
{
return count;
}
private:
Sigleton(){}
Sigleton(const Sigleton &){}
static Sigleton *m_p = new Sigleton ;
static int count;
五、类的友元函数
打破类外访问权限,类外对类内私有成员和保护成员访问权限。
可以设计为友元类或者友元函数。
两个类不能互为友元类。
int Sigleton::count;
class Point{
public:
private:
int m_x;
int m_y;
friend int Distance(Point p1,Point p2 );
};
int Distance(Point p1,Point p2 )
{
return (p1.m_x-p2.m_x);
}
int main()
{
Point p1,p2;
Distance(p1,p2);
cout<<"hello"<<endl;
return 0;
}
六、共享数据的保护
常成员函数:
在C++中函数后面加const表明函数的this指针是const修饰,这种函数称为常成员函数。
优点是:加大了传参的范围。
缺点:无法通过this指针修改数据成员。
注意 :
常成员函数内无法调用非常成员函数。
非常成员函数内可以调用常成员函数。
const在定义和声明处必须加。
七、volatile关键字
防止编译器做优化:
编译器会在内存和寄存器上保存两份数据,volatile作用是告诉编译器不要从寄存器上拿数据而是从内存中读取。
在qt中
const int i(100);
int*p = int(*)&i;
*p = 1001;
cout<<*p<<endl;
cout<<i<<endl;
加volatile关键字:
volatile const int i(100);
int*p = const_cast<int *>(&i);
*p = 1001;
cout<<*p<<endl;
cout<<i<<endl;
八、常数据成员
常数据成员必须初始化,且必须在初始化列表完成。