头文件:
头文件主要作用在于多个代码文件全局变量的重用、防止定义的冲突,对各个被调用函数给出一个描述,其本身不需要包含程序的逻辑实现代码,它只起描述性作用,用户程序只需要按照头文件中的接口声明来调用相关函数或变量,链接器会从库中寻找相应的实际定义代码。
以下定义一个person类
CPerson.h //.h文件是不参加编译的
class CPerson
{
private:
int m_nAge;
const int m_nName;
static int m_Sex;
public:
CPerson();
virtual ~CPerson();
public:
void AA();
void BB() const;
static void CC();
virtual void DD();
};
CPerson.cpp
#include "CPerson.h"
#include<iostream>
using namespace std;
CPerson::CPerson():m_nName(200)
{
m_nAge = 100;
cout << "CPreson" << endl;
}
CPerson::~CPerson()
{
cout << "Cperson" << endl;
}
void CPerson::AA()
{
cout << "CPerson::AA" <<endl;
}
void CPerson::BB() const
{
cout << "CPerson::BB" <<endl;
}
void CPerson::CC()
{
cout << "CPerson::CC" <<endl;
}
void CPerson::DD()
{
cout << "CPerson::DD" <<endl;
}
//static成员变量的初始化要在.cpp文件中
int CPerson::m_Sex = 1;
main.cpp
#include<iostream>
#include"CPerson.h"
using namespace std;
int main()
{
CPerson ps;
ps.AA();
ps.BB();
ps.CC();
ps.DD();
system("pause");
return 0;
}
运行结果
宏定义:
1.ifndef,意为判断没有定义宏怎么办,解决重复包含,需要和#endif,#define配合使用,ifndef与endif之间的代码只能调用一次
同样的,如果在同一个.cpp文件中调用了这个.h文件两次,编译器也只会执行一次。
2.pragma once //只编译一次
3.#define
变量
#include<iostream>
using namespace std;
#define M 20 //将代码中的M都代换成20
int main()
{
int arr[M];
for(int i = 0;i < M;i++)
arr[i] = i+1;
for(int i = 0;i < M;i++)
cout << arr[i] << endl;
system("pause");
return 0;
}
函数
#include<iostream>
using namespace std;
// \ 和下一行连接
#define AAAAA() \
for(int i = 0;i < 10;i++)\
cout << i << " ";
//带参数的,宏的参数页数替换的,##的意思是拼接
#define BBBBB(ThisClass) \
ThisClass ps;\
ps.Show();
#define CCCCC(ThisClass)\
ThisClass ps##ThisClass;\
ps##ThisClass.Show();
//#是转字符串
#define DDDDD(ThisClass) cout << ThisClass << endl;
//#define DDDDD(ThisClass) cout << #ThisClass << endl;
#define EEEEE(NAME) CPerson ps##Name;
class CPerson
{
public:
void Show()
{
cout << "CPerson::Show()" << endl;
}
};
class CSon :public CPerson
{
public:
void Show()
{
cout << "CSon::Show()" <<endl;
}
};
int main()
{
AAAAA()
cout<<endl;
BBBBB(CPerson)
CCCCC(CSon)
DDDDD("CPerson") //如果将类名直接传进去会报错,因为代换进去的是整个类而不仅仅是类名
//若不想在这里加引号,可以在宏定义时在使用变量前面加#
for(int i = 0;i < 10;i++)
EEEEE(i) //因为传递不是值传递,是单纯的替换,所以这里不会报错
//每一个循环都会回收生成的对象
//int i = 1;
//EEEEE(i);
//int i = 2;
//EEEEE(i); //这个会报错,会说你重定义
system("pause");
return 0;
}
4.#ifdef 判断有宏定义怎么办
UNICODE是系统宏定义,判断当前工程使用的是哪种字符集,如果是Unicode字符集时,使用MessageBoxW,如果是多字节字符集是,使用MessageBoxA。
void MessageBoxW(wchar_t* str)
{
}
void MessageBoxA(char* str)
{
}
这样就解决了复制代码时字符集不同导致的错误。
枚举:
枚举是一个被命名的整型常数的集合。
//表示纸牌的花色
enum CardsColor
{
CardsFlower,CardsBlack,CardsRed,CardsSquare
};
CardsColor calor; //枚举类型的变量
如果枚举没有初始化变量,则从第一个变量开始依次赋值为0,1,2......。
当其中的某个变量被赋值,后面的数值依次加1。
enumNum x {x1,x2=0,x3=50,x4};
则x1 = 0,x2 = 0,x3 = 50,x4 = 51。
枚举值是常量,不是变量,不能在程序中用赋值语句再对它赋值。
只能把枚举值赋予枚举变量,不能把元素的数值直接赋予枚举变量。如color=CardsFlower;是正确的,而color=0;是错误的。
内联函数:
内联函数是指那些定义在类体内的成员函数,即该函数的函数体放在类体内。
#include<iostream>
using namespace std;
//内联函数和宏的区别
//宏不检查错误,建议用内联函数,const,enum替换宏
inline void Show()
{
cout << "Show()" << endl;
}
//函数代码量少,调用次数比较频繁
int main()
{
Show(); //函数调用的地方,直接替换函数体里的代码
//(*pfn)(); //普通函数
//cout << "Show()" << endl; //内联函数
system("pause");
return 0;
}
#pragma once
#include<iostream>
class CPerson
{
public:
CPerson(void);
~CPerson(void);
public:
void Show() //在类(头文件里)实现的函数默认都是内联函数
{
std::cout << "CPerson::Show()" << std::endl;
}
};