当前位置: 首页 > news >正文

笔记C++语言,太焦虑了

调查研究

Javascript

基础知识

介绍

**javascript是一种运行在客户端(浏览器)的编程语言 ,实现人机交互效果 **

  1. 作用:网页特效、表单验证、数据交互、服务器编程(node.js)

组成:

  • ECMAScripts —> 规定js的基础语法核心知识
  • Web APIs —>
    • DOM 操作文档,比如对页面元素进行移动、大小、添加删除操作
    • BOM 操作浏览器,比如页面弹窗,检测窗口宽度、存储数据到浏览器
  1. 书写位置
  • 内部js —>写在html里面,用script标签,写在上面

  • 外部js —>代码写在js文件,引入html页面

  • 内联js —>代码写在标签内部

    <script> prompt("hello,world")document.write('你好,js')
    </script>
    
  • 注释

    单行注释 // 快捷键 Ctrl + /

​ 块注释 /* */ 快捷键 shift + alt + a

​ 结束符 —>英文分号代表语句结束 ;

  1. 输入输出语法

输出语法:向body输出内容 document.write('你好,js')

​ 页面警示框 alert('你好,js')

​ 控制台输出语法 console.log('你好,js')

输入语法: 提示输入prompt('请输入hello,world')

  1. 代码执行顺序

alert()和prompt()会跳过页面渲染先被执行

变量

  1. 变量的定义

变量是计算机存储数据的容器

  1. 变量的声明

创建变量:声明关键字、变量名

let 变量名

赋值:对变量进行初始化

let age = 18
//let不允许多次声明一个变量

交换两个变量的值,引入第三个变量temp

  1. 变量的本质

内存–>计算机存储数据的地方,程序在内存中申请一小块用来存放数据的小空间

  1. 变量的命名规范

由数字、字母、下划线、$符号组成,不能使用关键字,不能以数字开头;严格区分大小写

  • let和var的区别

var可以先使用在声明、声明过的变量可以重复声明;变量提升、全局变量、没有块级作用域

声明变量统一用let


  1. 常量

概念:是一个不能被修改的值,通常用于表示固定、不变的量,使用const变量

使用:const PI = 3.1415926

常量不允许重新赋值,声明的时候必须复制(初始化)

  1. 数据类型(弱数据类型语言)

①基本数据类型

number、string、boolean、undefined、null、

②引用数据类型

object、function、array

数字–number

  1. 定义:number 类型用于表示整数和浮点数,包括正数、负数和零

  2. 算术运算符 ( + - * / % >> 取余)

  3. 特别地:NaN是一个特殊的数值状态,它不等于任何值,包括自己,因此NaN != NaN

任何对NaN的操作都是返回NaN

字符串–string

  1. 用于存储文本数据的变量类型。字符串由字符组成,可以包含字母、数字、标点符号等;单引号、双引号、反引号包裹的数据
  2. 字符串拼接 ‘+’;
  3. 模版字符串

语法:``反引号

内容拼接变量时,用${ }包裹变量

${变量名}

其他类型

  • 布尔类型—boolean

是一种数据类型,用于表示逻辑值,只有两种可能的值:true 和 false

  • 未定义类型—undefined

未定义类型"通常指的是在程序运行时,遇到的与变量类型相关的错误;声明变量未赋值

  • 空类型—null

表示一个变量被赋值为 null,将来存放对象

类型转换

typeoftypeof ()—>用于获取变量的类型

let num = 10
typeof num 

隐式转换:+ 两边只要有字符串,默认为字符串计算,其他算术运算符为数字类型

+'123'可转为数字类型

Number( ) 函数可以将字符串转换为数字

parseInt( ) 函数用于将字符串转换为整数

parsefloat( ) 函数将字符串转换为浮点数

运算符

赋值运算符(=、+=)

对变量进行赋值的运算符

let b = 5;
b += 3; // b现在等于8,等同于b = b + 3
一元运算符(+)

只需要一个表达式就可运算,自增++和 自减–

自增运算符

  • 前缀形式(++a):先增加值,再使用该值。
  • 后缀形式(a++):先使用原值,再增加值。

自减运算符

  • 前缀形式(--a):先减少值,再使用该值。
  • 后缀形式(a--):先使用原值,再减少值。
比较运算符(> <)

比较运算符有隐式转换

  1. <=:小于等于
  2. ==:等于
  3. !=:不等于
  4. ===:严格等于
  5. !==:严格不等于
  • 字符串比较

字符串比较转换为对应的ASCII码比较

逻辑运算符&&

逻辑与(全真为真)—&&

逻辑或(一真则真)—||

逻辑非 (非真即假)—!

流程控制语句

  • 顺序结构>>从上到下、依次执行

  • 分支结构

    1. if条件为真就执行
    2. else否则执行这里
    3. switch匹配哪个 case 就执行哪个
  • 循环结构

    1. for计数循环,条件成立就继续
    2. while先判后做,成立才循环
    3. do...while先做后判,至少执行一次
    4. for用于遍历数据结构
    • for...of:获取元素值(如数组元素、字符串字符)
    • for...in:获取键名(如对象键、数组索引字符串)
  • break和continue

break:彻底结束循环,立即跳出。

continue:跳过当前迭代,继续下一轮循环

数组array

  1. 定义

​ 数组是一个有序的存储容器,用于存储多个值。这些值可以是 primitives(如字符串、数字、 boolean、 null、 undefined)或 objects(对象)、 arrays(数组)等复杂的值。

  1. 声明语法

let 数组名 = [数据]

  1. 访问

数组名[索引号]

长度–>数组的length获得:数组名.length

  1. 遍历

i <= array.length-1,确保索引不超过数组的最后一个元素(索引为 length-1)

进阶知识

HTML

基础知识

CSS

基础知识

Linux

基础知识

前景提要

  • 计算机的主要组成部分:硬件系统和软件系统

操作系统(Operating System, OS)是计算机系统中负责管理和控制计算机及其资源的核心软件;

移动操作系统

  1. 安卓(Android)
  2. iOS
  3. 鸿蒙(HarmonyOS)

PC操作系统

  1. Windows
  2. macOS
  3. Linux

Linux的主要发行版:Ubuntu/RedHat/Centos

Windows操作系统

WSL(Windows Subsystem for Linux

  • WSL2:基于轻量级虚拟机(Hyper-V),提供完整的Linux内核,文件系统性能大幅提升,推荐使用。

Linux知识

Linux系统的组成:linux系统内核、系统级应用程序

Linux目录结构
  1. 根目录 (/):
    • Linux系统的根目录是所有其他目录的起点,通常包含操作系统和系统配置文件。
  2. 常用目录层次结构:
    • /boot:包含操作系统启动所需的文件和分区。
    • /home:用户日志、配置文件等。
    • /root:根用户的目录,通常是系统管理员的主目录。
    • /etc:环境变量、系统配置文件。
    • /user:用户目录,存储用户程序和数据。
    • /mnt:挂载点,用于连接外置文件系统。
  3. 用户目录 (/user):
    • 用户目录下通常包含用户的配置文件、应用程序的安装目录、以及用户生成的文件等。
  4. 本地目录 (/user/local):
    • 用于存储用户的本地配置文件,如密码、登录信息等,通常隐藏在用户目录下。
  5. 设备驱动层:
    • /dev:包含设备驱动和虚拟设备,如swap分区、设备映射等。

Shell编程

C++程序设计语言

基础知识

变量

命名规则:C++标识符由字母、数字和下划线组成,必须以字母或下划线开头,不能是关键字,并且区分大小写

数据的输入与输出

cout是标准输出流对象,通过<<运算符向控制台输出数据(如cout << "Hello" << endl;),endl换行;

cin是标准输入流对象,通过>>从控制台读取输入到变量(如cin >> name;)。

两者需包含头文件<iostream>,属std命名空间。

<<称插入运算符,>>为提取运算符,注意输入类型需匹配变量,字符串输入用getline()更安全。

数据类型

C++数据类型包括基本类型:整型( int、long long int)、浮点型(如 float、double)、布尔型(如 true、false)、字符型(char)和字符串型(string)、复合类型(数组array、结构体、类、联合体)、空类型(void)及引用类型

sizeof 是 C++ 中的一个一元运算符,用于计算数据类型或变量在内存中所占的字节数,返回值为 size_t 类型

size_t—无符号整数类型,专门用来表示 “对象大小”“数组索引” 这类 非负整数值

  • sizeof(类型名)(如 sizeof(int)
  • sizeof 变量/表达式(如 sizeof(a)

科学计数法:

科学计数法的幂次是 10 的幂,float 精度约 7 位十进制,double 精度约 15 位

未指定后缀的科学计数法默认是 double 类型
例如:3e-2double,若赋值给 float 变量,添加后缀 fF

flaot f3 = 3e-2f =3*10^-2

double f3 = 3e+2 = 3*10^2

运算符

算术运算符
  • / :除法(整数除法会截断小数部分)整数相除结果依然是整数
  • %:取模(求余数,仅用于整数类型)
  • ++:自增
  • --:自减

前置运算符 — 变量先加减,再进行表达式运算;

后置运算符 — 先执行表达式运算,再进行变量加减

赋值运算符

=用于赋值,复合形式如+=*=可简化操作

比较运算符

用于判断两值关系,返回布尔值:

==相等、!=不等、>大于、<小于、>=大于等于、<=小于等于

逻辑运算符

&&:全真为真;||:一真即真;!:非真即假

条件运算符

语法格式为:
condition ? expression1 : expression2

#include <iostream>
using namespace std;int main() {int score = 85;// 条件运算符:condition ? expr1 : expr2// 如果条件为真,返回expr1;否则返回expr2string result = (score >= 60) ? "及格" : "不及格";cout << "分数 " << score << " 的结果是:" << result << endl;// 输出:分数 85 的结果是:及格return 0;
}

三目运算符返回的是变量,可以继续赋值

#include <iostream>
using namespace std;int main() {int a = 10;int b = 20;// 三目运算符返回的是变量本身(左值),所以可以继续赋值// 因为 a < b,所以 (a > b ? a : b) 返回的是 b 这个变量// 相当于执行了 b = 100(a > b ? a : b) = 100;cout << "a = " << a << ", b = " << b << endl; // 输出: a = 10, b = 100return 0;
}

流程结构

顺序结构

依次执行

  1. 程序从 main() 函数开始

  2. 逐行执行每条语句

  3. 每条语句执行完成后自动进入下一条

  4. 直到遇到 return 0; 程序结束

选择结构

if语句

简单if语句:if (条件) 语句;

  • 如果条件为真,执行语句;否则跳过

if-else语句:if (条件) 语句1; else 语句2;

  • 如果条件为真,执行语句1;否则执行语句2

if-else else-if语句:用于多条件判断

  • 依次检查每个条件,执行第一个为真的条件对应的语句

重要规则:

  • 条件表达式需要用圆括号 () 括起来
  • 如果if或else后面有多条语句,必须用花括号 {} 括起来形成代码块
  • C++中,非零值被视为真,零值被视为假

Switch语句

重要规则:

  • 类型限制:switch的判断表达式只能是整型(int, short, long等)或字符型(char),不能是浮点型、字符串或布尔型
  • 值匹配:只能匹配具体的值,不能判断区间(如case 60-70: 是错误的)
  • break的重要性:每个case后通常需要break语句,否则会"穿透"执行下一个case的代码
  • default可选:可以包含default分支处理未匹配的情况
#include <iostream>
using namespace std;int main() {char grade = 'B';cout << "成绩等级对应评语:" << endl;switch (grade) {case 'A':cout << "优秀!继续保持!" << endl;break;  // 必须有break,否则会继续执行下一个casecase 'B':cout << "良好!很有潜力!" << endl;break;case 'C':cout << "及格!需要更加努力!" << endl;break;case 'D':cout << "不及格!要加油了!" << endl;break;case 'F':cout << "很差!需要重新学习!" << endl;break;default:  // 处理未匹配的情况cout << "无效的成绩等级!" << endl;break;}// 错误示例:尝试使用区间(这是不允许的)/*int score = 85;switch (score) {case 90-100:  // 错误!不能使用区间cout << "A" << endl;break;case 80-89:   // 错误!cout << "B" << endl;break;}*/// 正确处理数值范围的方式应该用if-elseint score = 85;cout << "\n用if-else处理分数区间:" << endl;if (score >= 90) {cout << "等级:A" << endl;} else if (score >= 80) {cout << "等级:B" << endl;} else if (score >= 70) {cout << "等级:C" << endl;} else if (score >= 60) {cout << "等级:D" << endl;} else {cout << "等级:F" << endl;}return 0;
}
循环结构

1. while循环

  • 语法:while (条件) { 循环体 }

  • 执行流程:

    1. 判断条件表达式是否为真
    2. 如果为真,执行循环体,然后回到判断
    3. 如果为假,跳出循环,执行循环后的代码
    #include <iostream>
    using namespace std;int main() {int i = 1;// 当i <= 5时,重复执行循环体while (i <= 5) {cout << i << " ";i++;  // 更新循环变量}// 输出:1 2 3 4 5return 0;
    }
    

2. do while循环

  • 语法
do {// 循环体
} while (条件);
  • 重要规则:
    1. 至少执行一次:无论条件是否为真,循环体都会先执行一次
    2. 后判断:在每次循环体执行完毕后才检查条件
    3. 分号:while后的条件判断必须以分号结束
#include <iostream>
using namespace std;int main() {int i = 1;// 先执行循环体,再判断条件do {cout << i << " ";i++;} while (i <= 5);// 输出:1 2 3 4 5return 0;
}

3. for循环

  • 语法:
for (初始化; 条件; 更新) {// 循环体
}
  • 重要规则:
    1. 三要素集中:初始化、条件判断、更新操作都在括号内清晰定义
    2. 预测试:先判断条件,为真时才执行循环体
    3. 适用场景:适合循环次数已知的情况

数组是用于存储相同类型多个元素的连续内存空间

利用for循环遍历数组

#include <iostream>
using namespace std;int main() {int arr[5] = {10, 20, 30, 40, 50};// 使用for循环遍历数组for (int i = 0; i < 5; i++) {cout << "arr[" << i << "] = " << arr[i] << endl;}return 0;
}

猜数字案例

#include <iostream>      // 输入输出流
#include <ctime>         // time()函数获取时间
using namespace std;int main()
{cout << "猜数字游戏开始!" << endl;// 1. srand() + time(NULL):设置随机数种子// time(NULL)返回当前时间(秒数),确保每次运行程序产生不同的随机序列srand(time(NULL));// 2. rand() % 100 + 1:生成1-100的随机数// rand()产生0-RAND_MAX的随机数// % 100 得到0-99,+1 变成1-100int a = rand() % 100 + 1;int guess = 0;cout << "请输入你猜的数字(1-100):" << endl;// 3. while(true)无限循环 + break:实现持续猜测直到正确while (true) {cin >> guess;  // 输入// 4. if-else if-else:多分支判断if (guess > a) {cout << "猜大了" << endl;}else if (guess < a) {cout << "猜小了" << endl;}else {cout << "恭喜你猜对了" << endl;break;  // 5. break:跳出循环}}cout << "游戏结束" << endl;return 0;
}

4. 跳转语句

  • break

    1. 跳出循环**:在 forwhiledo-while 循环中,立即终止整个循环**
    2. 跳出switch:在 switch 语句中,跳出当前 switch 结构,防止"穿透"到下一个case

    break 只能跳出最内层的循环或 switch 语句

#include <iostream>
using namespace std;int main() {// break在循环中的使用for (int i = 1; i <= 10; i++) {if (i == 5) {break;  // 当i等于5时,立即跳出循环}cout << i << " ";  // 输出:1 2 3 4}return 0;
}
  • continue

    1. 跳过当前循环体中剩余的代码
    2. 直接进入下一次循环的迭代
    3. 对于 for 循环,会先执行更新表达式,再判断条件

    continue 只能在循环结构(forwhiledo-while)中使用。

#include <iostream>
using namespace std;int main() {// continue跳过偶数,只输出奇数for (int i = 1; i <= 10; i++) {if (i % 2 == 0) {continue;  // 如果是偶数,跳过本次循环剩余代码}cout << i << " ";  // 只有奇数能执行到这里}// 输出:1 3 5 7 9return 0;
}
  • **go to **
goto 标签名;
...
标签名: // 标签后跟冒号

​ 1. 无条件跳转:立即跳转到标签所在位置

​ 2. 标签命名:遵循变量命名规则,后跟冒号

​ 3. 作用范围:只能在同一函数内跳转

​ 4. 限制:不能跳过变量的初始化(如跳过带初始化的定义)

#include <iostream>
using namespace std;int main() {int i = 1;loop_start:  // 定义标签if (i > 5) {goto loop_end;  // 条件满足时跳转到loop_end}cout << i << " ";i++;goto loop_start;  // 跳转回loop_startloop_end:  // 标签位置cout << "\n循环结束" << endl;return 0;
}
// 输出:1 2 3 4 5
//       循环结束

数组

一维数组
  1. 声明语法类型 数组名[大小];
    • 类型:数组中所有元素的数据类型(如int、double、char等)
    • 大小:数组元素的个数,必须是编译时常量(正整数)
  2. 内存布局
    • 数组元素在内存中连续存储
    • 第一个元素的索引是0,最后一个元素的索引是大小-1
    • 可以通过&数组名[索引]获取元素的内存地址
  3. 初始化方式
    • 完全初始化:int arr[3] = {1, 2, 3};
    • 部分初始化:int arr[5] = {1, 2}; (剩余元素自动初始化为0)
    • 自动大小:int arr[] = {1, 2, 3}; (编译器根据初始化值确定大小)
  4. 访问元素
    • 使用下标运算符 [],如 arr[0]
    • 不检查边界:访问超出范围的索引会导致未定义行为(如内存越界)
  5. 数组名的含义
    • 数组名代表数组首元素的地址
    • sizeof(数组名) 返回整个数组的字节数
    • 作为函数参数传递时,会退化为指针
#include <iostream>
using namespace std;int main() {// 1. 声明并初始化一维数组int scores[5] = {85, 92, 78, 96, 88};  // 完全初始化// 2. 访问数组元素(使用for循环)cout << "=== 数组元素遍历 ===" << endl;for (int i = 0; i < 5; i++) {cout << "第" << (i+1) << "个成绩: " << scores[i] << endl;}// 3. 修改数组元素scores[2] = 85;  // 将第三个元素修改为85cout << "\n修改后第三位成绩: " << scores[2] << endl;// 4. 数组大小计算cout << "数组总大小: " << sizeof(scores) << " 字节" << endl;cout << "单个元素大小: " << sizeof(scores[0]) << " 字节" << endl;cout << "元素个数: " << sizeof(scores) / sizeof(scores[0]) << endl;// 5. 内存地址演示cout << "\n=== 内存地址 ===" << endl;for (int i = 0; i < 5; i++) {cout << "scores[" << i << "] 地址: " << &scores[i] << endl;}cout << "数组名地址: " << scores << endl;  // 数组名即首元素地址return 0;
}
二维数组
  1. 声明语法类型 数组名[行数][列数];

    • 例如:int matrix[3][4]; 声明一个3行4列的整型数组
  2. 内存布局

    • 元素在内存中连续存储
    • 按行优先顺序:第一行所有元素 → 第二行所有元素 → …
    • 总元素个数 = 行数 × 列数
    • 总字节数 = 行数 × 列数 × sizeof(元素类型)
  3. 初始化方式

    • 按行初始化:int arr[2][3] = {{1,2,3}, {4,5,6}};
    • 连续初始化:int arr[2][3] = {1,2,3,4,5,6};
    • 部分初始化:未指定的元素自动初始化为0
    #include <iostream>
    using namespace std;int main() {// 1. 完整按行初始化(推荐,清晰易读)int arr1[2][3] = {{1, 2, 3},{4, 5, 6}};// 2. 连续初始化(按内存顺序)int arr2[2][3] = {1, 2, 3, 4, 5, 6};// 等价于上面的arr1// 3. 部分初始化 - 只初始化前几行int arr3[3][4] = {{1, 2},           // 第0行:1,2,0,0{3, 4, 5}         // 第1行:3,4,5,0  // 第2行全部为0};// 4. 部分初始化 - 只初始化前几个元素int arr4[2][3] = {1, 2, 3, 4};// 等价于 {{1,2,3},{4,0,0}}// 5. 全部初始化为0int arr5[2][3] = {0};  // 所有元素都为0// 6. 省略行数,自动推断(列数必须指定)int arr6[][3] = {{1, 2, 3},{4, 5, 6},{7, 8, 9}};  // 编译器自动推断行数为3// 验证初始化结果cout << "=== 部分初始化示例(arr3) ===" << endl;for (int i = 0; i < 3; i++) {for (int j = 0; j < 4; j++) {cout << arr3[i][j] << "\t";}cout << endl;}// 输出:// 1    2    0    0// 3    4    5    0  // 0    0    0    0return 0;
    }
    

  4. 访问元素

    • 使用双下标:数组名[行索引][列索引]
    • 行索引范围:0 到 (行数-1)
    • 列索引范围:0 到 (列数-1)
    • 不进行边界检查,越界访问会导致未定义行为
  5. 数组名的含义

    • 数组名代表第一行的地址(即&数组名[0]
    • sizeof(数组名) 返回整个二维数组的总字节数
#include <iostream>
using namespace std;int main() {// 1. 声明并初始化二维数组int matrix[3][4] = {{1, 2, 3, 4},    // 第0行{5, 6, 7, 8},    // 第1行  {9, 10, 11, 12}  // 第2行};// 2. 遍历并输出二维数组cout << "=== 二维数组遍历 ===" << endl;for (int i = 0; i < 3; i++) {      // 行循环for (int j = 0; j < 4; j++) {  // 列循环cout << matrix[i][j] << "\t";}cout << endl;  // 每行结束后换行}// 3. 访问特定元素cout << "\nmatrix[1][2] = " << matrix[1][2] << endl;  // 输出7// 4. 数组大小信息cout << "总大小: " << sizeof(matrix) << " 字节" << endl;cout << "每行大小: " << sizeof(matrix[0]) << " 字节" << endl;cout << "元素类型大小: " << sizeof(matrix[0][0]) << " 字节" << endl;cout << "总元素个数: " << (sizeof(matrix) / sizeof(matrix[0][0])) << endl;return 0;
}

函数

  1. 函数的定义
返回类型 函数名(参数列表) {// 函数体(具体实现代码)[return 表达式;]  // 如果返回类型不是void,则需要return语句
}
  1. 函数的调用
  • 语法:函数名(实际参数列表);
#include <iostream>
using namespace std;// 函数定义
int add(int a, int b) {return a + b;
}void printResult(int result) {cout << "计算结果: " << result << endl;
}int main() {int x = 5, y = 3;// 函数调用示例int sum = add(x, y);           // 调用add函数,实参是变量x和yprintResult(sum);              // 调用printResult函数,实参是变量sumprintResult(add(10, 20));      // 嵌套调用:add的返回值作为printResult的参数printResult(add(x, 7));        // 实参可以是变量和常量的组合return 0;
}
  1. 函数的类别
  • 无参无返回值 (void function())
    1. 特点:不接收任何输入,也不返回结果
    2. 用途:执行固定操作,如显示菜单、打印信息
void showMenu() {cout << "=== 主菜单 ===" << endl;cout << "1. 开始游戏" << endl;cout << "2. 退出游戏" << endl;
}
  • 有参无返回值 (void function(parameters))
    • 特点:接收输入参数,但不返回结果
    • 用途:根据输入执行操作,如打印格式化信息
void printSum(int a, int b) {cout << a << " + " << b << " = " << (a + b) << endl;
}
  • 无参有返回值 (return_type function())
    • 特点:不接收输入,但返回一个计算结果
    • 用途:获取系统状态、生成随机数等
int getRandomNumber() {return rand() % 100 + 1;  // 返回1-100的随机数
}
  • 有参有返回值 (return_type function(parameters))

    特点:接收输入参数,并返回计算结果

    用途:最常用的函数类型,进行数据处理和计算

int add(int a, int b) {return a + b;  // 根据输入参数计算并返回结果
}

案例

#include <iostream>
#include <cstdlib>
#include <ctime>
using namespace std;// 1. 无参无返回值
void showMenu() {cout << "=== 计算器 ===" << endl;cout << "1. 加法" << endl;cout << "2. 退出" << endl;
}// 2. 有参无返回值
void printResult(int a, int b, int result) {cout << a << " + " << b << " = " << result << endl;
}// 3. 无参有返回值  
int getRandomNumber() {return rand() % 10 + 1;  // 返回1-10的随机数
}// 4. 有参有返回值
int add(int a, int b) {return a + b;
}int main() {srand(time(0));// 测试四种函数类型showMenu();                    // 无参无返int num1 = getRandomNumber();  // 无参有返int num2 = getRandomNumber();int sum = add(num1, num2);     // 有参有返printResult(num1, num2, sum);  // 有参无返return 0;
}
  1. 函数的分文件编写

创建.h后缀名的头文件,创建.cpp后缀名的源文件,头文件中写函数声明,源文件中写函数定义

头文件(.h 或 .hpp)

1. 包含函数声明(函数原型)2. 使用    `#ifndef`/`#define`/`#endif` 防止重复包含(头文件保护)3. 通过    `#include` 在其他文件中引用

源文件(.cpp)

​ 1. 包含函数的具体实现(定义)

​ 2. 实现头文件中声明的函数

主文件(main.cpp)

​ 1. 包含 main() 函数

​ 2. 引用头文件来使用其他文件中的函数

指针

  • 指针的作用:指针间接访问内存

      **指针是C++中一种特殊的变量,用于存储另一个变量的内存地址**
    
  • 语法

    数据类型* 指针变量名;

  • 指针初始化

    数据类型* 指针名 = &变量名; -------将变量的地址赋值给指针

  • &取地址

    取地址运算符(&) &变量名; ------获取变量的内存地址

  • 解引用运算符(*) *指针名 -------访问指针所指向地址中的值

  • 指针所占内存空间

    1. 大小固定
      • 在同一系统上,所有类型指针的大小都相同
      • 与指向 intdoublechar 等无关
    2. 系统依赖
      • 32位系统:指针占 4字节(32位 = 4字节)
      • 64位系统:指针占 8字节(64位 = 8字节)
    3. 使用 sizeof
      • sizeof(指针变量)sizeof(数据类型*) 可获取指针大小
#include <iostream>
using namespace std;int main() {int value = 42;// 1. 指针声明int* ptr;// 2. 指针初始化(使用取地址符&)ptr = &value;// 3. 解引用(使用*获取指向的值)cout << "value的值: " << value << endl;cout << "ptr指向的值: " << *ptr << endl;cout << "value的地址: " << &value << endl;cout << "ptr存储的地址: " << ptr << endl;// 4. 通过指针修改值*ptr = 100;cout << "修改后value: " << value << endl;// 5. 空指针ptr = nullptr;  // 安全的空指针return 0;
}

空指针指向的内存,不允许访问,访问空指针所指向的内存是非法的

  1. 空指针的本质
    • 值为 nullptr(或 NULL0
    • 不指向任何有效的内存位置
    • 是一种安全的"无指向"状态
常量指针(Pointer to const)
  • 语法const 数据类型* 指针名数据类型 const* 指针名
  • 含义:指针指向的数据不能修改,但指针本身可以指向其他地址
  • 记忆法:“指向常量的指针”
int a = 10, b = 20;
const int* ptr = &a;  // ptr指向常量整数// ✅ 允许:改变指针指向
ptr = &b;  // ptr现在指向b// ❌ 禁止:修改指针指向的数据
// *ptr = 30;  // 错误!不能通过ptr修改数据
指针常量(Const pointer)
  • 语法数据类型* const 指针名
  • 含义:指针本身是常量,指向的地址不能改变,但可以修改指向的数据
  • 记忆法:“常量的指针”
int a = 10, b = 20;
int* const ptr = &a;  // ptr是一个常量指针,初始化指向a// ✅ 允许:修改指针指向的数据
*ptr = 15;  // a的值变为15// ❌ 禁止:改变指针指向
// ptr = &b;  // 错误!ptr是常量,不能重新赋值
常量指针常量(完全常量)
  • 语法const 数据类型* const 指针名
  • 含义:既不能改变指向的地址,也不能修改指向的数据
int a = 10, b = 20;
const int* const ptr = &a;// ❌ 都不允许
// *ptr = 20;   // 错误!不能修改数据
// ptr = &b;    // 错误!不能改变指向

口诀

  • const* 左边:数据常量(指针可变)

  • const* 右边:指针常量(数据可变)

  • const两边:都是常量

  • **指针和数组 **

    1. 数组名的本质
      • 数组名是一个指向首元素的指针常量
      • arr 等价于 &arr[0]
      • 不能修改数组名的指向(因为是常量)
    2. 指针算术
      • 指针加减整数会按指向类型的大小移动
      • ptr + 1 移动 sizeof(类型) 个字节
    • sizeof(arr) 返回整个数组的字节数
    • sizeof(ptr) 返回指针变量的大小
#include <iostream>
using namespace std;int main() {int arr[5] = {10, 20, 30, 40, 50};// 1. 数组名作为指针cout << "arr = " << arr << endl;           // 数组首地址cout << "&arr[0] = " << &arr[0] << endl;   // 首元素地址cout << "*arr = " << *arr << endl;         // 10(首元素值)// 2. 指针指向数组int* ptr = arr;  // 等价于 int* ptr = &arr[0];// 3. 两种访问方式等价性cout << "\n=== 访问方式对比 ===" << endl;for (int i = 0; i < 5; i++) {cout << "arr[" << i << "] = " << arr[i] << ", *(arr+" << i << ") = " << *(arr + i)<< ", *(ptr+" << i << ") = " << *(ptr + i) << endl;}// 4. 指针遍历cout << "\n=== 指针遍历 ===" << endl;for (int* p = arr; p < arr + 5; p++) {cout << *p << " ";}cout << endl;// 5. 重要区别int* dynamicArr = new int[3]{1, 2, 3};cout << "sizeof(arr) = " << sizeof(arr) << endl;      // 整个数组大小cout << "sizeof(ptr) = " << sizeof(ptr) << endl;      // 指针大小cout << "sizeof(dynamicArr) = " << sizeof(dynamicArr) << endl; // 指针大小delete[] dynamicArr;return 0;
}
  • 指针和函数

    1. 指针作为函数参数
    • 概念:将指针作为参数传递给函数
    • 优点 :
      • 避免大数据的复制开销

      • 实现函数间的双向通信(修改原数据)

      • 处理动态分配的内存

结构体

  1. 结构体的定义
struct 结构体名 {数据类型 成员1;数据类型 成员2;// ...
};
  1. 结构体数组

  2. 结构体指针

  3. 结构体嵌套结构体

  4. 结构体做函数参数

  5. const使用场景

  6. 结构体案例

通讯管理系统案例

内存四区

内存分区模型:代码区、全局区、栈区、堆区

代码区;只读、共享

全局区:全局变量和静态变量(static)/常量(字符串常量,const修饰的全局变量)

栈区的注意事项:不要返回局部变量的地址、栈区的数据在函数执行完成后自动释放

堆区:

new 数据类型 new返回的是该数据类型的指针;

释放数据delete 释放数组 delete [ ]

#include <iostream>
using namespace std;int main() {// --- 栈区示例 ---int stackVar = 50;  // 栈区,函数结束自动释放// --- 堆区示例 ---int* heapPtr = new int(100);      // 堆区分配int* heapArray = new int[5]{1,2,3,4,5};  // 堆区分配数组cout << "*heapPtr = " << *heapPtr << endl;// 使用完必须释放delete heapPtr;        // 释放单个intdelete[] heapArray;    // 释放数组// 避免悬空指针heapPtr = nullptr;heapArray = nullptr;return 0;
}

引用

  1. 引用的作用

    替代指针实现引用传递

    语法:数据类型 &别名 = 原名;

  2. 引用的注意事项

    必须初始化:引用在声明时就必须绑定到一个对象

    绑定后不可更改:引用一旦初始化,就不能再指向其他对象

    绑定对象必须存在:不能引用不存在的变量(如已销毁的局部变量)

  3. 引用做函数参数

    返回类型 函数名(类型& 参数名) {// 函数体
    }
    
  4. 引用做函数返回值(函数调用做左值)

  5. 引用的本质是指针常量

  6. 常量引用主要用来修饰形参

进阶知识

函数高级

函数的默认参数(函数声明有默认参数,函数实现就不能有默认参数)

从右向左原则:默认参数必须从右向左依次定义

只能在声明中指定:通常在头文件中声明时设置默认值

不能重复指定:定义时不能再写默认值

函数重载(函数的返回值不可以作为函数重载的条件)

​ 允许在同一作用域内定义多个同名函数,只要它们的参数列表不同

满足:同一个作用域、函数名称相同、函数参数类型不同或顺序不同或个数不同

重载的条件

函数重载必须满足以下至少一个条件:

条件示例
参数个数不同func() vs func(int a)
参数类型不同func(int a) vs func(double a)
参数顺序不同func(int, double) vs func(double, int)

类和对象

C++面向对象的三大特性:封装、继承、多态

封装
  1. 什么是封装
  • 将相关的数据(属性)和函数(方法)组织在一个类中
  • 隐藏对象的内部实现细节
  • 通过公共接口与外界交互
  1. 封装的好处
  • 安全性:防止外部直接修改内部数据
  • 易维护性:内部实现可以改变而不影响外部代码
  • 复用性:封装好的类可以被多次使用
  • 简化使用:用户只需了解公共接口

类(class)

class 类名 {
private:    // 私有成员(默认)// 数据成员(属性)// 成员函数
protected:  // 保护成员// ...
public:     // 公有成员// 成员函数(接口)
};
  1. 访问控制
    • private:只能在类内部访问(默认)
    • public:可以在任何地方访问
    • protected:在类内部和派生类中访问
  2. 成员组成
    • 数据成员:描述对象的属性
    • 成员函数:描述对象的行为
  3. 对象创建
    • 类名 对象名;
    • 对象通过.操作符访问公有成员

实例化

类中的属性和行为统一称为成员

struct和class的区别

默认的访问权限不同struct(public)/class(prviate)

特性structclass
默认访问权限publicprivate
默认继承方式publicprivate
使用习惯侧重数据组织侧重面向对象设计

成员属性设置私有

对象的初始化和清理

1.构造函数和析构函数

​ 构造函数语法:类名(){ }

关键特征:

  • 没有返回类型(连 void 都不能写)

  • 函数名必须与类名完全相同

  • 在创建对象时自动调用

    构造函数的特点

特性说明
无返回值不能写任何返回类型
自动调用对象创建时自动执行,无需手动调用
只调用一次每个对象在其生命周期内仅调用一次
可重载可以有多个构造函数(参数不同)
可带参数支持参数初始化成员变量
#include <iostream>
using namespace std;class Timer {
public:// 构造函数:开始计时Timer() {cout << "计时开始..." << endl;}// 析构函数:结束计时~Timer() {cout << "计时结束!" << endl;cout << "任务完成!" << endl;}
};void doWork() {Timer t;  // 创建对象,自动开始计时// 模拟做一些工作cout << "正在处理数据..." << endl;cout << "正在保存文件..." << endl;cout << "正在清理缓存..." << endl;// 函数结束时,t的析构函数自动被调用
}int main() {cout << "程序开始" << endl;doWork();  // 调用函数cout << "程序结束" << endl;return 0;
}

​ 析构函数:~类名(){ }

析构函数的核心特点

特性说明
没有返回值不能写任何返回类型(包括void)
无参数不能有任何参数(包括void)
自动调用对象销毁时自动执行
只调用一次每个对象在其生命周期内仅调用一次
不能重载一个类只能有一个析构函数
class 类名 {
public:// 构造函数 - 没有返回值,名字和类一样类名() {// 对象创建时自动执行}// 析构函数 - 名字前面加~~类名() {// 对象销毁时自动执行}
};

2.构造函数的分类及调用

构造函数的分类:

  1. 按参数分类
类型示例
无参构造Person() { }
有参构造Person(string name, int age) { }
  1. 按功能分类
类型说明
普通构造包括无参和有参构造
拷贝构造Person(const Person& p) { }

拷贝构造函数:

#include <iostream>
#include <string>
using namespace std;class Dog {
public:string name;Dog(string n) : name(n) {cout << "创建: " << name << endl;}// 拷贝构造函数Dog(const Dog& other) {name = "copy_of_" + other.name;cout << "复制: " << other.name << " → " << name << endl;}
};int main() {Dog dog1("旺财");           // 普通构造Dog dog2(dog1);             // 调用拷贝构造// 输出: 复制: 旺财 → copy_of_旺财Dog dog3 = dog1;            // 也调用拷贝构造// 输出: 复制: 旺财 → copy_of_旺财return 0;
}

注意事项:调用默认构造函数,不要加(),会被认为是一个函数的声明

Person p; // ✅ 调用无参构造,创建对象
Person p( ); // ❌ 这是一个函数声明!不是创建对象

拷贝构造函数调用时机:

1.使用一个已经创建完毕的对象来初始化一个新对象

2.值传递的方式给函数参数传值

3.值方式返回局部对象

class Person {
public:// 拷贝构造函数Person(const Person& p) {cout << "拷贝构造函数被调用" << endl;}
};int main() {Person p1;// 1. 用已创建的对象初始化新对象Person p2(p1);        // ✅Person p3 = p1;       // ✅// 2. 值传递给函数参数void func(Person p);  // 传参时调用拷贝构造func(p1);// 3. 值方式返回局部对象Person create() {Person temp;return temp;  // 返回时可能调用拷贝构造}return 0;
}

构造函数调用规则:创建一个类,编译器会给每个类都添加至少3个函数

分别是默认构造函数默认析构函数拷贝构造(值拷贝)

如果用户定义有参构造函数,c++不提供默认无参构造,会提供默认拷贝构造

如果用户定义拷贝构造函数,c++不会在提供其他构造函数

3. 深拷贝与浅拷贝

4.初始化列表

5.类对象作为成员

6.静态成员

7.对象模型和this指针

8.友元

9.运算符重载

继承
多态

提高知识

模版

C++的另一种编程思想称为泛型编程,主要利用的技术就是模版;

C++提供两种模版机制:函数模版类模版

模版的语法:

template<typename T>
函数声明或定义解释:
template ---声明创建模版
typename ---表明其后面的符号是一种数据类型,可以用class代替
T ---通用的数据类型,通常为大写字母

注意事项:

自动类型推导,必须推导出一致的数据类型T,才可以使用

模版必须要确定出T的数据类型,才可以使用

普通函数与函数模版区别:

普通函数调用可以发生隐式类型转换,函数模板调用不会发生隐式类型转换

如果利用显示指定类型的方式,可以发生隐式类型转换

普通函数与函数模版的调用规则:

如果函数模版和普通函数都可以实现,优先调用普通函数

可以通过空模版参数列表来强制调用函数模版

函数模版也可以发生重载

如果函数模版可以产生更好的匹配,优先调用函数模版

类模版

语法:

template <typename T>
类解释:
template  ---声明创建末模板
typename ---表明其后面的符号是一种数据类型,可以用class代替
T   ---通用的数据类型

STL(Standard Template Library)

STL基本概念

STL从广义上分为容器(container)算法(algorithm)迭代器(iterator)

算法和容器之间通过迭代器进行无缝连接

STL六大组件

容器、算法、迭代器、仿函数、适配器(配接器)、空间配置器

1.容器:各种数据结构,如vector、list、deque、set、map等,用来存放数据

2.算法:各种常用的算法

3.迭代器:扮演了容器与算法之间的胶合剂

4.仿函数:行为类似函数

5.适配器:一种用来修饰容器或者仿函数或迭代器接口的东西

6.空间配置器:负责空间的配置与管理

容器:

STL容器就是将运用最广泛的一些数据结构实现出来

常用的数据结构:数组、链表、树、队列、集合、映射表等

这些容器分为序列式容器和关联式容器:

​ 序列式容器:强调值的排序,序列式容器中的每个元素均有固定的关系

​ 关联式容器:二叉树结构,各元素之间没有严格的物理上的顺序关系

算法(ALgorithms)

算法分为:质变算法和非质变算法

​ 质变算法:是指运算过程中会更改区间内元素的内容,例如拷贝、替换、删除等等

​ 非质变算法:是指运算过程中不会更改区间内元素内容,例如查找、计数、遍历、寻找极值等

迭代器:

提供一种方法,使之能够依寻访问某个日期所含的各个元素,而有又无需暴露该容器的内部表示方式

种类:

种类功能支持运算
输入迭代器对数据的只读访问只读,,++、==、!=
输出迭代器对数据的只写访问只写,++
前向迭代器读写操作,并向前推进迭代器读写,++、==、!=
双向迭代器读写操作,并能向前和向后操作读写,++,–
随机访问迭代器读写操作,可以以跳跃的方式访问任意数据读写,++,–,[n],-n、<、<=、>、>=

容器算法迭代器初识

vector存放内置数据类型

容器: vector

算法: for_each

迭代器: vector<int>::iterator

Java 程序设计语言

Python程序设计语言

http://www.dtcms.com/a/549226.html

相关文章:

  • 分公司一般做网站吗音乐网站建设目标
  • Java 21 虚拟线程 vs 缓存线程池与固定线程池
  • 在线开发培训网站建设小型餐饮店面设计
  • ZYNQ USB按键读写操作详解:从裸机到Linux系统的完整实现
  • 如何在Windows桌面实现自由悬浮计时?
  • BEV环视感知算法从环境部署开始
  • 看上去高端的网站深圳培训学校
  • 狂飙与重构:机器人IPO浪潮背后的系统焦虑与感知进化
  • 21.静态NAT
  • 做头像的网站wordpress拖拽式
  • 【C++】位运算算法习题
  • 券商上云,不止AI和大数据,还有USB Server
  • 软件设计师知识点总结:面向对象技术(设计模式)
  • 广西建设局建设行政主管部网站企业app开发企业
  • Python 实战:Web 漏洞 Python POC 代码及原理详解(3)
  • VMware替代 | ZStack ZSphere与VMware NSX安全策略对比
  • BigDecimal
  • 【电子元器件·10】低功耗继电器 —— 磁保持继电器;有源蜂鸣器、无源蜂鸣器
  • 示范专业网站建设网站开发体会范文
  • LeetCode 411 - 最短独占单词缩写
  • 日语学习-日语知识点小记-构建基础-JLPT-N3阶段-二阶段(11):文法和单词-第三课
  • 网站建设方案和报价家装设计师工资高吗
  • 虚拟环境配置
  • 高效学习《数据库原理》:从理论到实战的计算机专业指南
  • 龙口网站设计网站文件夹没有权限设置
  • Vue3+CSS 实现3D卡片动画
  • RabbitMQ面试全解析:从核心概念到高可用架构
  • MATLAB数据读取全攻略从TXT到音视频的详细方法解析
  • 用ps做网站切片高级感ppt模板免费
  • 21.动态NAT