一、注释
1.单行注释
Ctrl+/
// 注释
2.多行注释
Shift+Alt+A
/* 注释 */
二、输入输出
cin>>变量;
cout<<变量;
三、数据类型
作用:给变量分配一个合适的内存空间
数据类型 | 占用空间 | 取值范围 | |
---|---|---|---|
整型 | short(短整型) | 2字节 | |
int(整型) | 4字节 | ||
long(长整型) | 4字节 | ||
long long(长长整型) | 8字节 | ||
实型(浮点型) | float(单精度) | 4字节 | 7位有效数字 |
double(双精度) | 8字节 | 15-16位有效数字 | |
字符型 | char | 1字节 | |
字符串型 | string | ①chat 变量名[] = "" ②string 变量名 = "" | |
布尔类型 | bool | 1字节 | true\false |
四、转义字符
转义字符 | 描述 |
---|---|
\a | 警报 |
\b | 退格,将当前位置移到前一列 |
\f | 换页,将当前位置移到下一页开头 |
\n | 换行,将当前位置移到下一行开头 |
\r | 回车,将当前位置移到本行开头 |
\t | 水平制表 |
\v | 垂直制表 |
\\ | 代表一个反斜线字符 |
\' | 单引号 |
\" | 双引号 |
\? | 问号 |
\0 | 0 |
\ddd | 八进制转义字符 |
\xhh | 16进制转义字符 |
五、变量
作用:给一段制定的内存空间起名,方便操作这段内存
语法
数据类型 变量名 = 变量初始值
int a = 10;
六、常量
作用:用于记录程序中不可更改的数据
语法
方式一:#define 宏常量:
#define 常量名 常量值
通常在文件上方定义,表示一个常量
方式二:const 修饰的变量:
const 数据类型 变量名 = 常量值
通常在变量定义前加关键字const,修饰该变量为常量,不可修改
七、关键字
注:在给变量和常量起名时,不要用C++的关键字。
asm | do | if | return | typedef |
---|---|---|---|---|
auto | double | inline | short | typeid |
bool | dynamic_cast | int | signed | typename |
break | else | long | sizeof | union |
case | enum | mutable | static | unsigned |
catch | explicit | namespace | static_cast | using |
char | export | new | struct | virtual |
class | extern | operator | switch | void |
const | false | private | template | volatile |
const_cast | float | protected | this | wchar_t |
continue | for | public | throw | while |
default | friend | register | true | |
delete | goto | reinterpret_cast | try |
八、标识符(变量、常量)命名规则
-
标识符不能是关键字
-
标识符只能由字母、数字、下划线组成
-
第一个字符必须为字母或下划线
-
标识符中字母区分大小写
九、运算符
1.算术运算符
+ | / | % |
---|---|---|
- | + | ++ |
* | - | -- |
前置和后置的区别
-
前置递增(递减),先让变量+1(-1),然后再进行表达式运算;
-
后置递增(递减),先进行表达式运算,然后再让变量+1(-1)。
2.赋值运算符
= | *= |
---|---|
+= | /= |
-= | %= |
3.比较运算符
== | > |
---|---|
!= | <= |
< | >= |
4.逻辑运算符
运算符 | 术语 | 示例 | 描述 |
---|---|---|---|
! | 非 | !a | 如果a为假,则为真;如果a为真,则为假 |
&& | 与 | a&&b | 如果a与b都为真,则结果为真;否则为假 |
|| | 或 | a||b | 如果a和b有一个为真,则结果为真,二者都为假时,结果为假 |
十、程序流程结构
1.顺序结构
2.选择结构
(1)if语句
if(条件){满足条件执行的语句}
if(条件){满足条件执行的语句} else {不满足条件执行的语句}
if(条件1){满足条件1执行的语句} else if (条件2){满足条件2执行的语句} ... else {不满足条件执行的语句}
嵌套if语句
(2)三目运算符:a>b?a:b(返回的是变量,可以继续赋值)
(3)switch语句
switch(表达式){
case 结果1:执行语句; break;
case 结果2:执行语句; break;
...
default:执行语句; break;
}
3.循环结构
(1)while循环
while(表达式){
循环语句;
}
(2)do...while循环
do{
循环语句;
}while(表达式)
(3)for循环
for(起始表达式;条件表达式;末尾循环体){
循环语句;
}
4.跳转语句
-
break语句:跳出选择结构或循环结构
-
continue语句:在循环语句中,跳过本次循环中余下尚未执行的语句,继续执行下一次循环
-
goto语句:可以无条件跳转语句
#include <iostream>
using namespace std;
int main() {
cout<<"short : "<<sizeof(short)<<endl;
goto FLAG;
cout<<"int : "<<sizeof(int)<<endl;
cout<<"long : "<<sizeof(long)<<endl;
FLAG:
cout<<"long long : "<<sizeof(long long)<<endl;
return 0;
}
结果:
short : 2
long long : 8
十一、数组
1.一维数组
数组就是一个集合,里面存放了相同类型的数据元素。
语法
数据类型 数据名[数组长度];
数据类型 数据名[数组长度] = {值1,值2,....};
数据类型 数据名[] = {值1,值2,....};
特点
-
放在一块连续的内存空间中
-
数组中每个元素都是相同数据类型
-
数组元素下标从0开始
一维数组名的用途
-
可以统计整个数组在内存中的长度
-
可以获得数组在内存中的首地址
int arr[]={1,2,3};
cout<<sizeof(arr)<<endl;
cout<<arr<<endl;
cout<<(long long)arr<<endl;
cout<<&arr[0]<<endl;
cout<<(long long)&arr[0]<<endl;
结果:
0x61fe14
6422036
0x61fe14
6422036
冒泡排序算法
#include <iostream>
#include <math.h>
using namespace std;
int main() {
int arr[]={4,2,8,0,5,7,1,3,9};
int n=sizeof(arr)/sizeof(arr[0]);
for(int i=0;i<n;i++){
cout<<arr[i]<<" ";
}
cout<<endl;
for(int i=0;i<n/2+1;i++){
for(int j=0;j<n-i-1;j++){
int temp=0;
if(arr[j]>arr[j+1]){
temp=arr[j];
arr[j]=arr[j+1];
arr[j+1]=temp;
}
}
}
for(int i=0;i<n;i++){
cout<<arr[i]<<" ";
}
cout<<endl;
return 0;
}
结果
4 2 8 0 5 7 1 3 9
0 1 2 3 4 5 7 8 9
2.二维数组
语法
数据类型 数据名[行数][列数];
数据类型 数据名[行数][列数] = {{值1,值2},{值3,值4}};
数据类型 数据名[行数][列数] = {值1,值2,值3,值4};
数据类型 数据名[][列数] = {值1,值2,值3,值4};
十二、函数
作用:将一段经常使用的代码封装起来,减少重复代码。
语法
1.无参无返
返回值类型 函数名(){
函数体语句;
}
2.有参无返
void 函数名(形式参数列表){
函数体语句;
}
3.无参有返
返回值类型 函数名(){
函数体语句;
return 表达式;
}
4.有参有返
返回值类型 函数名(形式参数列表){
函数体语句;
return 表达式;
}
函数的调用
语法
方式一:函数在main函数前面定义的调用方式
函数名(实际参数)
方式二:函数在main函数后面定义的调用方式
函数声明:返回值类型 函数名()
函数名(实际参数)
值传递
函数调用时实参将数值传入给形参;如果函数的形参发生变化,并不会影响实参。
#include <iostream>
using namespace std;
void swap(int c,int d){
int temp=c;
c=d;
d=temp;
}
int main() {
int a=2,b=6;
swap(a,b);
cout<<a<<endl;
cout<<b<<endl;
}
结果:
2
6
十三、指针
作用:可以通过指针间接访问内存
-
内存编号是从0开始记录的,一般十六进制数字表示
-
可以利用指针变量保存地址
语法
数据类型 * 变量名;
1.定义指针
int a=10;
int * p;
// 方式一
p = &a;
// 方式二
// int * p = a;
2.使用指针
*P = 5;
无论什么数据类型,指针都是占8个字节空间大小。
空指针:指针变量指向内存中编号为0的空间
用途:初始化指针变量
注意:空指针是不可以访问的(0-255之间的内存编号是系统占用的,因此不可以访问)
int * p = NULL;
野指针:指针变量指向非法的内存空间
const修饰指针
(1)const修饰指针——常量指针
const int * p = a;
特点:指针的指向可以修
改,但是指针的值不可以修改
(2)const修饰常量——指针常量
int * const p = a;
特点:指针的指向不可以修改,但是指针的值可以修改
(3)const即修饰指针,又修饰常量
const int * const p = a;
特点:指针的指向不可以修改,指针的值也不可以修改
指针和数组
int arr[5]={1,2,3,4,5};
cout<<"第一个元素为:"<<arr[0]<<endl;
int * p = &arr;
cout<<"第一个元素为:"<<*p<<endl;
cout<<"第二个元素为:"<<*++p<<endl;
指针和函数
地址传递
#include <iostream>
using namespace std;
void swap(int *c,int *d){
int temp=*c;
*c=*d;
*d=temp;
}
int main() {
int a=2,b=6;
swap(&a,&b);
cout<<a<<endl;
cout<<b<<endl;
}
结果:
6
2
#include <iostream>
#include <math.h>
using namespace std;
void bubbleSort(int n,int *arr){
for(int i=0;i<n/2+1;i++){
for(int j=0;j<n-i-1;j++){
int temp=0;
if(arr[j]>arr[j+1]){
temp=arr[j];
arr[j]=arr[j+1];
arr[j+1]=temp;
}
}
}
}
void print(int n,int *arr){
for(int i=0;i<n;i++){
cout<<arr[i]<<" ";
}
cout<<endl;
}
int main() {
int arr[]={4,2,8,0,5,7,1,3,9};
int n=sizeof(arr)/sizeof(arr[0]);
cout<<"排序前:";
print(n,arr);
bubbleSort(n,arr);
cout<<"排序后:";
print(n,arr);
return 0;
}
结果:
排序前:4 2 8 0 5 7 1 3 9
排序后:0 1 2 3 4 5 7 8 9
十四、结构体
概念:用户自定义的数据类型,允许用户存储不同的数据类型
语法
struct 结构体名 { 结构体成员列表 };
通过结构体创建变量的方式有三种(struct可以省略):
-
struct 结构体名 变量名
-
struct 结构体名 变量名 = {成员1值, 成员2值,...}
-
定义结构体时顺便创建变量
#include <iostream>
using namespace std;
// 结构体定义
struct Student{
// 成员列表
string name;
int age;
int score;
}s3;
int main(){
struct Student s1;
s1.name="张三";
s1.age=18;
s1.score=90;
cout<<"姓名:"<<s1.name<<","<<"年龄:"<<s1.age<<","<<"成绩:"<<s1.score<<endl;
struct Student s2={"张三",18,90};
cout<<"姓名:"<<s2.name<<","<<"年龄:"<<s2.age<<","<<"成绩:"<<s2.score<<endl;
s3.name="李四";
s3.age=18;
s3.score=90;
cout<<"姓名:"<<s3.name<<","<<"年龄:"<<s3.age<<","<<"成绩:"<<s3.score<<endl;
return 0;
}
结构体数组
作用:将自定义的结构体放入到数组中方便维护
语法
struct 结构体名 数组名[元素个数] = {{},{},...{}}
#include <iostream>
using namespace std;
// 结构体定义
struct Student{
// 成员列表
string name;
int age;
int score;
};
int main(){
struct Student arr[3]={
{"张三",18,90},
{"李四",18,90},
{"王五",18,90},
};
for(int i=0;i<3;i++){
cout<<"姓名:"<<arr[i].name<<","<<"年龄:"<<arr[i].age<<","<<"成绩:"<<arr[i].score<<endl;
}
return 0;
}
结构体指针
作用:通过指针访问结构体中的成员
-
利用操作符 -> 可以通过结构体指针访问结构体属性
#include <iostream>
using namespace std;
// 结构体定义
struct Student{
// 成员列表
string name;
int age;
int score;
};
int main(){
struct Student s={"张三",18,90};
cout<<"姓名:"<<s.name<<","<<"年龄:"<<s.age<<","<<"成绩:"<<s.score<<endl;
struct student * p = &s;
cout<<"姓名:"<<p->name<<","<<"年龄:"<<p->age<<","<<"成绩:"<<p->score<<endl;
return 0;
}
嵌套结构体
作用:结构体中的成员可以是另一个结构体
例如:每个老师辅导一个学员,一个老师的结构体中,记录一个学生的结构体
总结:在结构体中可以定义另一个结构体作为成员,用来解决实际问题
#include <iostream>
using namespace std;
// 结构体定义
struct Student{
// 成员列表
string name;
int age;
int score;
};
struct teacher{
int id;
string name;
int age;
struct Student stu;
}
int main(){
teacher t;
t.id = 10000;
t.name = "老王";
t.age = 50;
t.stu.name = "小王";
t.stu.age = 20;
t.stu.score = 60;
cout<<"老师姓名:"<<t.name<<","<<"老师编号:"<<t.id<<","<<"老师年龄:"<<t.age<<"学生姓名:"<<t.stu.name<<","<<"学生年龄:"<<t.stu.age<<","<<"学生成绩:"<<t.stu.score<<endl;
return 0;
}
结构体做函数参数
作用:将结构体作为参数向函数中传递
传递方式有两种:
-
值传递
-
地址传递
#include <iostream>
using namespace std;
// 结构体定义
struct Student{
// 成员列表
string name;
int age;
int score;
};
// 值传递
void printStudent1(student s){
s.age = 28;
cout<<"姓名:"<<s.name<<","<<"年龄:"<<s.age<<","<<"成绩:"<<s.score<<endl;
}
// 地址传递
void printStudent2(student * p){
p->age = 28;
cout<<"姓名:"<<p->name<<","<<"年龄:"<<p->age<<","<<"成绩:"<<p->score<<endl;
}
int main(){
struct Student s={"张三",18,90};
printStudent1(s);
cout<<"姓名:"<<p->name<<","<<"年龄:"<<p->age<<","<<"成绩:"<<p->score<<endl;
printStudent2(&s);
cout<<"姓名:"<<p->name<<","<<"年龄:"<<p->age<<","<<"成绩:"<<p->score<<endl;
return 0;
}
结果:
张三,28,90
张三,18,90
张三,28,90
张三,28,90
结构体中const使用场景
作用:用const来防止误操作
#include <iostream>
using namespace std;
// 结构体定义
struct Student{
// 成员列表
string name;
int age;
int score;
};
void printStudent2(const student * p){
p->age = 28; // 加入const之后,一旦有修改的操作就会报错,可以防止我们误操作
cout<<"姓名:"<<p->name<<","<<"年龄:"<<p->age<<","<<"成绩:"<<p->score<<endl;
}
int main(){
struct Student s={"张三",18,90};
printStudent(&s);
cout<<"姓名:"<<p->name<<","<<"年龄:"<<p->age<<","<<"成绩:"<<p->score<<endl;
return 0;
}
实例:通讯录管理系统
系统需求
-
添加联系人:想通讯录中添加新人,信息包括(姓名、性别、年龄、联系电话、家庭住址)最多记录1000人
-
显示联系人:显示通讯录中所有联系人信息
-
删除联系人:按照姓名进行删除指定联系人
-
查找联系人:按照姓名查看指定联系人信息
-
修改联系人:按照姓名重新修改指定联系人
-
清空联系人:清空通讯录中所有信息
-
退出通讯录:退出当前使用的通讯录
#include <iostream>
#include <string>
using namespace std;
#define NUM 1000 // 通讯录最多人数
// 菜单界面
void showMeun(){
cout<<"1.添加联系人"<<endl;
cout<<"2.显示联系人"<<endl;
cout<<"3.删除联系人"<<endl;
cout<<"4.查找联系人"<<endl;
cout<<"5.修改联系人"<<endl;
cout<<"6.清空联系人"<<endl;
cout<<"0.退出通讯录"<<endl;
}
struct Person{
string name;
int sex;
int age;
string phone;
string address;
};
struct Addressbooks{
struct Person p[NUM];
int size; // 当前通讯录人数
};
// 1.添加联系人函数
void addPerson(Addressbooks * abs){
if(abs->size==NUM){
cout<<"通讯录已满,无法添加。"<<endl;
}
else{
cout<<"请输入姓名:"<<endl;
string name;
cin>>name;
abs->p[abs->size].name=name;
while(true){
cout<<"请输入性别(1.男 2.女):"<<endl;
int sex = 0;
cin>>sex;
if(sex == 1 || sex == 2){
abs->p[abs->size].sex=sex;
break;
}
cout<<"输入有误,请重新输入。"<<endl;
}
cout<<"请输入年龄:"<<endl;
int age=0;
cin>>age;
abs->p[abs->size].age=age;
cout<<"请输入手机号:"<<endl;
string phone;
cin>>phone;
abs->p[abs->size].phone=phone;
cout<<"请输入地址:"<<endl;
string address;
cin>>address;
abs->p[abs->size].address=address;
// 更新通讯录人数
abs->size++;
cout<<"添加成功"<<endl;
// 按任意键继续
system("pause");
// 清屏操作
system("cls");
}
}
// 2.显示联系人函数
void showPerson(Addressbooks * abs){
if (abs->size == 0){
cout<<"当前记录为空"<<endl;
}
else{
for(int i=0;i<abs->size;i++){
cout<<"姓名:"<<abs->p[i].name<<"\t";
cout<<"性别:"<<(abs->p[i].sex==1?"男":"女")<<"\t";
cout<<"年龄:"<<abs->p[i].age<<"\t";
cout<<"电话:"<<abs->p[i].phone<<"\t";
cout<<"地址:"<<abs->p[i].address<<endl;
}
}
// 按任意键继续
system("pause");
// 清屏操作
system("cls");
}
// 检测联系人是否存在
int isExist(Addressbooks * abs, string name){
for(int i=0;i<abs->size;i++){
if(abs->p[i].name==name){
return i;
}
}
return -1;
}
// 3.删除联系人函数
void deletePerson(Addressbooks * abs){
cout<<"请输入要删除的联系人:"<<endl;
string name;
cin>>name;
int ret = isExist(abs,name);
if(ret != -1){
for(int i=ret;i<abs->size;i++){
abs->p[i]=abs->p[i+1];
}
abs->size--;
cout<<"删除成功"<<endl;
}
else{
cout<<"查无此人"<<endl;
}
// 按任意键继续
system("pause");
// 清屏操作
system("cls");
}
// 4.查看联系人函数
void findPerson(Addressbooks * abs){
cout<<"请输入要查看的联系人"<<endl;
string name;
cin>>name;
int ret = isExist(abs,name);
if(ret!=-1){
cout<<"姓名:"<<abs->p[ret].name<<"\t";
cout<<"性别:"<<abs->p[ret].sex<<"\t";
cout<<"年龄:"<<abs->p[ret].age<<"\t";
cout<<"电话:"<<abs->p[ret].phone<<"\t";
cout<<"住址:"<<abs->p[ret].address<<endl;
}
else{
cout<<"查无此人"<<endl;
}
// 按任意键继续
system("pause");
// 清屏操作
system("cls");
}
// 5.修改联系人函数
void modifyPerson(Addressbooks * abs){
cout<<"请输入要修改的联系人姓名:"<<endl;
string name;
cin>>name;
int ret = isExist(abs,name);
if(ret!=-1){
string name;
cout<<"姓名:"<<endl;
cin>>name;
abs->p[ret].name=name;
while(true){
cout<<"性别(1.男 2.女):"<<endl;
int sex=0;
cin>>sex;
if(sex==1||sex==2){
abs->p[ret].sex=sex;
break;
}
else{
cout<<"输入有误,请重新输入"<<endl;
}
}
cout<<"年龄:"<<endl;
int age=0;
cin>>age;
abs->p[ret].age=age;
cout<<"电话:"<<endl;
string phone;
cin>>phone;
abs->p[ret].phone=phone;
cout<<"住址:"<<endl;
string address;
cin>>address;
abs->p[ret].address=address;
}
else{
cout<<"查无此人"<<endl;
}
// 按任意键继续
system("pause");
// 清屏操作
system("cls");
}
void cleanPerson(Addressbooks * abs){
abs->size=0;
cout<<"通讯录已经清空"<<endl;
// 按任意键继续
system("pause");
// 清屏操作
system("cls");
}
int main(){
Addressbooks abs;
abs.size=0;
int select = 0;
while(true){
showMeun();
cin>>select;
switch(select){
case 1:
addPerson(&abs);
break;
case 2:
showPerson(&abs);
break;
case 3:
deletePerson(&abs);
break;
case 4:
findPerson(&abs);
break;
case 5:
modifyPerson(&abs);
break;
case 6:
cleanPerson(&abs);
break;
case 0:
cout<<"欢迎下次使用"<<endl;
return 0;
break;
}
}
return 0;
}