大卫信奥 · J1知识点总结 · 直播课

J1 知识点 · 五单元合集

从 C++ 的第一行代码,到数据类型、格式化输出与第一次综合练习。
一个学期,五段旅程——

01 环境与入门02 运算符03 数据类型04 格式化 I/O05 习题课
← 返回主页
J1 封面插图
课程目录
大卫信奥 · J1 知识点 · 一单元
01

C++ 从这里开始

认识 Dev-C++ 与 OJ,写出第一个程序,学会变量、输入与输出。

环境与工具 基本语法 输入输出 习题讲解
C++ 从这里开始封面
今日路线

四个环节,从工具走到第一个完整程序

01
环境篇
打开 Dev-C++,看懂错误提示,在 OJ 提交作业。
02
语法篇
四则运算、变量与赋值、变量命名规则。
03
输入输出
用 cin 读数据、用 cout 写结果。
04
习题讲解
综合练习:输出字符菱形。
01
PART 01 · 环境篇

先把工具用好

写代码、看错误、交作业——第一步是熟练使用 Dev-C++ 和 OJ。

Dev-C++ 错误提示 OJ 提交
Dev-C++ 使用

四步,写出并运行你的第一个程序

1
打开 Dev-C++
双击图标进入主界面。
2
新建源代码
文件 → 新建 → 源代码。
3
保存文件
文件 → 保存 / Ctrl+S。
4
编译并运行
编译运行,无错误即成功。
Dev-C++ · 源程序编辑器
文件 编辑 编译 运行
#include <iostream> using namespace std; int main() { cout << "Hello, World!" << endl; return 0; }
Dev-C++ 错误提示

报错不是坏事:红线告诉你错在哪里

错误提示是线索,不是失败——先把提示读一遍,再动手改。

Dev-C++ · 编译失败
源代码(第 4 行被标红)
#include <iostream> using namespace std; int main() { cout << "Hello"← 少了一个分号 return 0; }
输出窗口
[Error] expected ';' before '}' Line: 4 Column: 5
看红色行
编译失败时,代码里会用红色标出出错位置,下方输出窗口显示具体错误信息。
修改,再编译
找到错误位置修改代码,重新编译运行,直到没有错误提示为止。
OJ 使用

收藏 OJ,找到你的作业

https://oj.davidoi.com.cn/rs/
大卫信奥 Online Judge
登录 团队 J1 团队 团队习题集
复制代码 粘贴到文本框
点击绿色提交 总分 100
1
登录并收藏
打开网址登录,把网站收藏起来。
2
进入 J1 团队
点击“团队”,找到 J1 的团队。
3
打开团队习题集
点击“团队习题集”看作业。
提交后查看测试点详情:总分 100 说明代码正确,否则需要修改再提交。
02
PART 02 · 语法篇

C++ 的地基

运算、变量、命名规则——这些小零件组合起来就是程序。

四则运算 变量与赋值 命名规则
C++ 基本语法

加、减、乘、除——注意整数除法

+
加法
1 + 100
减法
100 - 1
×
乘法
2 × 50
/
除法
5 / 2 = 2
/
整数除法会丢掉小数部分。
5 / 2 的结果是 2,不是 2.5。
练一练:cout << 1 + 100 的输出是什么?
A101
B1+100
C1+100=101
D1+100=1
选 A:101 —— 程序会先算出 1 + 100,再输出结果。
C++ 基本语法

变量是装数据的盒子,赋值是把数据放进去

=
定义:类型 变量名;  赋值:变量名 = 值;
创建变量 → 放进数据
int a; // 创建变量 a = 10; // 变量赋值
aint
10
盒子类型 int
装上 10
blong long
10000000000
整数太大?
long long
常见类型
int long long double char string
C++ 基本语法

重新赋值:最后一次赋值生效

可以反复赋值,以最后为准
int a = 10; a = 20; // a 现在是 20 int b = a; // b 拿到 a 的值:20
aint
20
重新赋值
旧值 10 被覆盖
bint
20
int b = a;
复制 a 的值给 b
!
小技巧:交换 a 和 b 的值
int temp = a; // ① 暂存 a a = b; // ② a 换成 b b = temp; // ③ b 取回值
C++ 基本语法

变量名:四条规则,过一遍再起名

1
组成
字母、数字、下划线
2
开头
不能以数字开头
3
关键字
不能是关键字
4
大小写
a 和 A 是不同变量
练一练:下列变量名哪些是合法的?
A____
B1a
Ca1 / a2
D__b
Ea__1
Fa1_
G11_a
合法:A、C、D、E、F,非法:B、G。
03
PART 03 · 输入输出篇

程序和你对话

cin 从键盘读数据,cout 把结果写到屏幕。

cin 输入 cout 输出
C++ 输入输出

cin:从键盘读数据

cin 会根据变量的类型自动读入,不需要额外的类型转换。scanf 也能输入,留到后面章节再讲。

读入一个整数
int a; cin >> a; // 把输入存进变量 a
运行窗口
输入:10 ↓ 变量 a = 10
连续读入多种类型
int a; double b; char c; string d; cin >> a >> b >> c >> d;
运行窗口
输入:10 3.14 A Hello ↓ a=10 b=3.14 c='A' d="Hello"
练一练

先不看键盘放什么,猜猜输出是什么

程序
int x = 10, y = 20; cin >> x >> y; // 输入:1 2 cout << x << " " << y;
输入 1 2 (两个数用空格隔开) → 覆盖原值,输出 1 2
程序的输出是什么?
A10 20
B1 2
C2 1
D10 2
选 B:输入覆盖原值,输出 1 2。
!
cin 会把新输入的数覆盖原来的值——变量里最后放进去的才是它的值。
C++ 输入输出

cout:把数据输出到屏幕

整数、浮点数、字符、字符串都可以直接输出,endl 换行\n 也可以。printf 留到后面章节再讲。

输出一个变量并换行
int a = 10; cout << a << endl;
输出:10(并换行)
多种类型一起输出
int a = 10; double b = 3.14; char c = 'A'; string d = "Hello!"; cout << a << " " << b << " " << c << " " << d;
输出:10 3.14 A Hello!
04
PART 04 · 习题篇

综合挑战

用今天的全部知识,做一道完整的输出题。

拆解思路 编写代码 运行验证
习题讲解 · 输出字符菱形

写代码前,先数清楚每行有几个空格

*
***
*****
***
*
空格星号样子
121*
213***
305*****
413***
521*
#
上半部分空格 −1、星号 +2,
下半部分正好对称。
习题讲解 · 输出字符菱形

一行一行 cout,注意开头的空格

#include <bits/stdc++.h> using namespace std; int main() { cout << " *" << endl; cout << " ***" << endl; cout << "*****" << endl; cout << " ***" << endl; cout << " *" << endl; return 0; }
运行结果
*
***
*****
***
*
每行开头的空格也要原样输出
小结

今天你学会了:

环境篇
打开 Dev-C++ 编译与运行 看懂错误提示 在 OJ 提交作业
语法篇
四则运算 定义变量 变量命名规则
输入输出
cin 输入 cout 输出 输出字符菱形
课后任务:OJ · J1 作业,100 分通过。下一单元:更多数据类型与 if 分支。
拓展 · 带余除法

除不尽的整数:商和余数

/ 得商,% 得余数
int a = 7, b = 3; cout << a / b << " " << a % b << endl;
输出:2 1  先得商 2,余数 1
% 运算:只取余数
7 % 3 = 1
10 % 2 = 0
17 % 4 = 1
%
判断奇偶很常用:x % 2 == 0 就是偶数。
大卫信奥 · J1 知识点 · 二单元
02

运算符、表达式与数位分离

认识 + - * / % 五个运算符,会写表达式,把整数的每一位拆出来。

运算符 表达式 关键字 数位分离
运算符、表达式与数位分离封面
今日路线

五个环节,从运算符走到完整程序

01
运算符
+ - * / %,特别注意整除与取模。
02
表达式
常量、变量、运算符组成,有优先级。
03
自赋值与关键字
a=a+1 的简写,不能当变量名的词。
04
数位分离
用整除和取模拆出每一位数字。
01
PART 01 · 运算符与表达式

C++ 的算数运算

加减乘除取模,再加上表达式和优先级——先学会算,再学会算得对。

五个运算符 表达式 优先级
C++ 基本语法

加、减、乘、除、取模——五个基本运算符

+
加法
1 + 100
减法
100 - 1
×
乘法
2 × 50
/
除法
5 / 2 = 2
%
取模
10 % 3 = 1
/
/ 两边都是整数时,结果仍是整数(整除):5 / 2 得 2,不是 2.5% 取模只能用于整数,不能用于浮点数。
C++ 基本语法

表达式 = 常量 + 变量 + 运算符

表达式是一个计算式,值是算出来的结果,可以有常量,也可以有变量。

1 + 3
1 和 3 是常量
(1+2)*3-4/5
多个运算符
a + b * c
a b c 都是变量
a + 1
变量 + 常量
!
优先级:括号最高,乘除 / 取模高于加减。 例:2 + 3 × 4 = 14(2 + 3) × 4 = 20
练一练

先别看答案,猜猜屏幕上打出什么

程序
cout << 1 << "+" << 100 << "="; cout << 1 + 100 << endl;
程序的输出是什么?
A101
B1+100
C1+100=101
D1+100=1
选 C:先输出文字 1+100=,再算出 101,连成 1+100=101。
练一练

输入长方形长和宽,输出周长和面积

输入两个整数(1~20 之间),输出周长和面积,用空格隔开。

程序
int a, b; cin >> a >> b; cout << 2*(a+b) << " " << a*b << endl;
输入:8 5
输出:26 40
!
周长 = 2 × (a + b),面积 = a × b
验证
2 × (8+5) = 26,8 × 5 = 40
练一练

买文具:50 元能买几本,剩多少?

明明拿 50 元买练习本,一本 3 元,最多能买多少本?还剩多少钱?

程序
cout << 50 / 3 << " " << 50 % 3 << endl;
输出:16 2
/
数量 = 总价 ÷ 单价,剩余 = 取模。
50 / 3
16
最多能买
16 本
50 % 3
2
还剩
2 元
练一练

算出下面每个表达式的值

/ 得商,% 得余,从左到右逐级计算。

3 / 10
0
3 % 10
3
100 / 8 / 2
6
20 % 5
0
23 % 10
3
47 % 7 % 2
1
%
从左到右算:47 % 7 = 5,再 5 % 2 = 1100 / 8 = 12,再 12 / 2 = 6
02
PART 02 · 自赋值与关键字

把值算给自己

a = a + 1 有更短的写法,还有一类单词不能拿来当变量名。

自赋值 += -= *= /= 关键字
C++ 基本语法

自赋值:把变量自己的值算一遍,再放回自己

=
a = a + 1 意思是:把 a 的值加 1,再赋回 a。
写法对照
int a = 1; a = a + 1; // 等价于 a += 1 a = a - 1; // 等价于 a -= 1 a = a * 2; // 等价于 a *= 2 a = a / 2; // 等价于 a /= 2
aint
1
a += 1 后
a 变成 2
aint
2
a *= 2 后
a 变成 4
练一练

跟着代码一步步算,a 和 c 最后是多少?

程序
int a = 2, b = 3, c = 8; a -= b; // a = a - b = 2 - 3 = -1 c *= a; // c = c * a = 8 × (-1) = -8
aint
-1
a -= b
2 - 3 = -1
cint
-8
c *= a
8 × (-1) = -8
结果:a = -1,c = -8。
C++ 基本语法

关键字:语言里有特殊意义的单词

关键字不能用作变量名、函数名或其它标识符

int
整数类型
int a = 10;
float
浮点类型
float b = 3.14;
if
条件语句
二选一分支
while
循环语句
条件成立就重复
for
循环语句
数次数循环
还有很多
return / break 等
!
全部关键字查这里(延伸):cppreference.com/w/cpp/keyword
03
PART 03 · 数位分离

把一个整数拆开来

用整除和取模,把 12345 的每一位都取出来——这是很多题目的第一步。

除 10^n 取余 % 10 三位数反转
C++ 基本语法 · 数位分离

先除以 10 的幂,再对 10 取余

取某一位:先 / 10^n 把这一位移到个位,再 % 10 取出来

万位
1
千位
2
百位
3
十位
4
个位
5
取千位(= 2)
12345 / 1000 = 12 12 % 10 = 2
取百位(= 3)
12345 / 100 = 123 123 % 10 = 3
#
规律:第 k 位 = (n / 10^(k-1)) % 10 例:12345 / 1000 = 12,再 % 10 = 2。
练一练

把 461 反转成 164

分别取出个位、十位、百位,再组合起来。

程序
int n; cin >> n; // 输入 461 int g = n % 10; // 个位 1 int s = n / 10 % 10; // 十位 6 int b = n / 100; // 百位 4 cout << g*100 + s*10 + b; // 164
输出:164
个位 g = 461 % 10 = 1
十位 s = 461 / 10 % 10 = 6
百位 b = 461 / 100 = 4
组合:1×100 + 6×10 + 4 = 164。
04
PART 04 · 习题讲解

用今天学的知识做题

四道题:先读题,再想公式,最后写代码、看运行结果。

A+B (a+b)×c 带余除法
习题讲解 · A+B 问题

给定两个整数,输出它们的和

程序
#include <iostream> using namespace std; int main() { int a, b; cin >> a >> b; cout << a + b << endl; return 0; }
运行窗口
输入:3 5 输出:8
+
cin 读入 a、b,cout 输出它们的和。
习题讲解 · (a+b) × c

先求 a+b,再乘以 c

程序
#include <iostream> using namespace std; int main() { int a, b, c; cin >> a >> b >> c; cout << (a + b) * c << endl; return 0; }
运行窗口
输入:2 3 4 输出:20
( )
括号改变优先级:(2+3)×4 = 20
习题讲解 · 带余除法

/ 得商,% 得余

程序
#include <iostream> using namespace std; int main() { int a, b; cin >> a >> b; cout << a / b << " " << a % b << endl; return 0; }
运行窗口
输入:7 3 输出:2 1
%
7 / 3 得商 2,7 % 3 得余 1
! 思考题:等差数列末项怎么算?(点右上方进入)
小结

今天你学会了:

运算符与表达式
+ - * / % 整除 % 只能整数 优先级:括号 > 乘除% > 加减
自赋值与关键字
a = a + 1 += -= *= /= 关键字不能当变量名
数位分离
先除 10^n,再 % 10 三位数反转 带余除法
课后任务:OJ · J1 作业,100 分通过。下一单元:更多数据类型与 if 分支。
思考题 · 等差数列末项

末项 = 首项 + 公差 × (项数 − 1)

相邻两项的差是常数,即公差。例:1, 3, 5, 7, 9 公差为 2。

程序
int a, b, d, n; cin >> a >> b >> n; // a1, a2, 项数 d = b - a; cout << a + d * (n - 1) << endl;
输入:1 3 5 输出:9
a
a_n = a_1 + (n − 1) × d
其中 d = b − a 是公差
延伸阅读
题面:oj.davidoi.com.cn/rs/show_problem/447
还有等比数列、斐波那契数列。
大卫信奥 · J1 知识点 · 三单元
03

C++ 的数据类型

整数、浮点、字符、布尔——把数据放进正确的盒子,是写好 C++ 的第一步。

整数类型 浮点数 字符与 ASCII 类型转换
C++ 的数据类型封面
今日路线

四个部分,把数据类型的家底摸清

01
整数篇
有符号、无符号、整型溢出。
02
浮点篇
float、double 与精度误差。
03
字符篇
char、ASCII 码、字符运算。
04
bool 与转换
bool、隐式与显式类型转换。
01
PART 01 · 整数篇

把整数装进正确的盒子

有符号、无符号、溢出——范围的边界决定它能装多大的数。

有符号整型 无符号整型 整型溢出
有符号整型

能装负数,也能装正数——范围各有不同

类型字节取值范围
char1-128 ~ 127-2^7 ~ 2^7-1
short2-32768 ~ 32767-2^15 ~ 2^15-1
int4-2147483648 ~ 2147483647-2^31 ~ 2^31-1
long4-2147483648 ~ 2147483647-2^31 ~ 2^31-1
long long8-9223372036854775808 ~ 9223372036854775807-2^63 ~ 2^63-1
i
提示 · 二进制与字节
数字底层只有 0 / 1,每一位叫一个比特(bit), 8 个比特组成 1 个字节(byte)。上表的大小就是类型占的字节数, 字节数决定它能表示的范围(如 char → -128 到 127)。
练一练

整型快到边界时,会发生什么?

下面的程序输出什么?(int a = 2147483647)
int a = 2147483647; cout << a << endl; cout << a + 1 << endl;
A2147483647, 2147483648
B2147483647, -2147483648
C2147483647, 0
D编译错误
选 B:a 是 int 最大值,a+1 溢出翻回负数 -2147483648。
下面的程序输出什么?(unsigned int a = 0)
unsigned int a = 0; cout << a - 1 << endl;
A-1
B0
C4294967295
D编译错误
选 C:0 - 1 回绕到最大值 4294967295(2^32-1)。
无符号整型

只装非负数——范围从 0 开始

类型字节取值范围
unsigned char10 ~ 2550 ~ 2^8-1
unsigned short20 ~ 655350 ~ 2^16-1
unsigned int40 ~ 42949672950 ~ 2^32-1
unsigned long40 ~ 42949672950 ~ 2^32-1
unsigned long long80 ~ 184467440737095516150 ~ 2^64-1
!
不能表示负数:把负数赋给无符号变量,或运算中变成负数,都会溢出、结果出乎意料。
整型溢出

装满了,会从另一端冒出来

当 char 的值是 127
char x = 127; cout << int(x) << endl; // 127 x = x + 1; cout << int(x) << endl; // -128
输出:127 -128
x · char
127
+1
x · char
-128
越过上界 127,回绕到最小值 -128
这就是整型溢出
i
提示 · 为什么 127 + 1 是 -128?
这与二进制表示方式有关:计算机里有三种表示整数的方式——原码、反码、 补码。有兴趣的同学可以自行查阅相关资料。
02
PART 02 · 浮点数篇

小数也有自己的盒子

浮点数能表示小数,但表示是有限的——小心精度误差。

float / double 精度问题
浮点数类型

三种浮点类型:日常用 double 就够

类型字节大约取值范围说明
float4±1.2e-38 ~ ±3.4e38精度较低,不推荐
double8±2.2e-308 ~ ±1.8e308常规选择,够用
long double16±3.4e-4932 ~ ±1.2e4932精度高,几乎不用
d
几乎不用 long double,因为精度太高、占内存大。一般用 double 即可, 没要求时不推荐 float:精度低、易出误差。
练一练

float 算出来的小数,真的精确吗?

程序
float a = 1.0, b = 3.0; cout << a / b << endl;
程序的输出是什么?
A0.333333
B0.333333343
C0.33
D0.3
选 B:float 精度有限,1/3 存成 0.333333343。
!
这就是为什么日常建议用 double:它精度更高,误差更小。
浮点数精度问题

别用 == 直接比较小数

直接相等 · 出错
double a = 0.1, b = 0.2, c = 0.3; if (a + b == c) cout << "true"; else cout << "false";
输出:false (不相等)
?
0.1、0.2、0.3 无法精确表示,二进制是无限循环。
用误差范围 · 正确
double a = 0.1, b = 0.2, c = 0.3; if (abs(a + b - c) < 1e-9) cout << "true"; else cout << "false";
输出:true (误差极小)
用很小的误差范围 abs(a-b) < 1e-9 判断相等。
!
比较浮点数时,应避免直接用 ==,改用很小的误差范围判断是否相等。
03
PART 03 · 字符篇

字符背后,其实是数字

char 存字符也存整数——ASCII 码是中间那座桥。

字符类型 ASCII 码 字符运算
字符类型

char:字符、整数、转义字符都可以

char 只占 1 字节,本质是一个整数,可以拿来存字符、整数或转义字符。

三种存法
char a = 'a'; // 字符 char b = 66; // 整数 → 字符 'B' char c = '\n'; // 转义字符:换行
存整数 66,读出来就是字符 'B'。
#
常用的转义字符:\n 换行、\t 制表、\r 回车。
\0
\0 是特殊字符(ASCII 值 0),表示字符串结束
例如 "hello" 在内存里是 {'h','e','l','l','o','\0'}。
ASCII 码

字符 ↔ 数字:ASCII 对照表

'A'65
'a'97
'0'48
' '32
大写字母 A - Z
65 ~ 90
小写字母 a - z
97 ~ 122
数字 0 - 9
48 ~ 57
常用特殊字符
空格 32 · \n 10 · \r 13 · \t 9
练一练:下面的 ASCII 码对应什么字符?
65 97 48 32
AA a 0 空格
Ba A 0 空格
CA a 空格 0
D0 a A 空格
选 A:65→A,97→a,48→0,32→空格。
int 与 char 的关系

字符和整数:一个盒子可以互相转换

char ↔ int 互转
cchar
'A'
nint
65
int n = c
取 ASCII 值
dchar
'B'
66int
66
char d = 66
转成字符
字符运算 · 大小写差 32
cout << (char)('A' + 1); // 'B' cout << ('B' - 'A'); // 1 cout << ('A' < 'a'); // 1 char lo = 'A' + 32; // 'a' char up = 'b' - 32; // 'B'
小写 = 大写 + 32('A'→'a','b'→'B')。
练一练:下面程序的输出?
char c = 'A'; int n = c; cout << n << endl; // ? n = 66; c = n; cout << c << endl; // ?
AA B
B65 66
C65 B
DA 66
选 C:n=65,c='B'。
练一练 · 字符

字符和 ASCII:再算两道

下面程序的输出是什么?
char c1 = 'A', c2 = 65; int n1 = 'B', n2 = c1 + 1; cout << c1 << " " << c2 << " " << n1 << " " << n2 << endl;
AA A B 66
B65 A 66 B
CA A 66 66
DA 65 B 66
选 A:c1='A',c2=65→'A',n1='B'→66,n2=c1+1→66。
下面程序的输出是什么?
cout << ('z' - 'a') << endl; cout << ('9' - '0') << endl; cout << (char)('a' + 3) << endl;
A25 9 c
B25 9 d
C26 9 d
D26 9 c
选 B:'z'-'a'=25,'9'-'0'=9,'a'+3='d'。
04
PART 04 · bool 与类型转换

真假,以及类型的转换

bool 只有真和假,类型转换要小心丢失信息。

bool 类型 隐式转换 显式转换
布尔类型

bool:真和假,本质是 1 和 0

true / false 存成 1 / 0
bool a = true, b = false; cout << a << endl; // 1 cout << b << endl; // 0
=
bool 占 1 字节,可隐式转换:非 0 值变 true(1),0 变 false(0)。
练一练:下面程序的输出?
bool a = 5, b = -3, c = 0; cout << a << " " << b << " " << c << endl;
A5 -3 0
B1 1 0
Ctrue true false
D5 -3 false
选 B:5 和 -3 都转成 true(1),0 转成 false(0)。
类型转换

类型转换:会自动,也可以手动

隐式转换 · 自动
int a = 1; double b = a; // int 自动转 double
b = 1.0 朝精度更高的方向自动转
显式转换 · 手动
double a = 1.23; int b = (int)a; // C 风格 int c = static_cast<int>(a); // 更安全
b = 1,c = 1 小数部分被截掉
!
转换风险:精度丢失数据溢出符号丢失未定义行为
练一练:a=3, b=2,输出是什么?
cout << a / b << endl; cout << (double)a / b << endl;
A1 1.5
B1.5 1.5
C1 1
D编译错误
选 A:1 和 1.5。
习题讲解

两道题:一个防溢出,一个取 ASCII 值

A × B · 用 long long 防溢出
#include <iostream> using namespace std; int main() { long long a, b; cin >> a >> b; cout << a * b << endl; return 0; }
!
数据范围大,用 long long 存结果,防止 int 溢出。
打印 ASCII 码 · int(c)
#include <iostream> using namespace std; int main() { char c; cin >> c; cout << int(c) << endl; return 0; }
!
用 int(c) 输出输入字符的 ASCII 码,用 char 类型存字符。
小结

今天你学会了:

整数篇
有符号整型 无符号整型 整型溢出
浮点与字符
float / double 浮点精度 char 与 ASCII
布尔与转换
bool 1 / 0 隐式转换 显式转换
课后任务:OJ · J1 作业,100 分通过。下一单元:第四单元,继续深入数据类型与更多语法。
大卫信奥 · J1 知识点 · 四单元
04

自增自减与格式化输入输出

搞懂 ++ 和 -- 的取值顺序,学会 scanf 与 printf 精确控制输入输出。

自增自减 scanf printf 精度控制
自增自减与格式化输入输出封面
今日路线

三个环节,把 ++/-- 和格式化输出用熟

01
自增与自减
前缀/后缀取值、复合赋值、字符自增、优先级。
02
格式化输入输出
scanf 输入、printf 输出、特殊格式、精度控制。
03
精度与习题
float/double 差异、浮点比较、日期格式化、习题讲解。
01
PART 01 · 自增与自减篇

先搞清楚 ++ 和 -- 怎么取值

前缀先加后取值,后缀先取值后加,复合赋值就是它的简写。

自增自减 复合赋值 字符自增 优先级
C++ 自增与自减

前缀 ++x 先加后取值,后缀 x++ 先取值后加

前缀:++x 先加后取值
int x = 5; cout << ++x << endl; // 输出 6
x
5
++x 的值
6
先加 1 再取值,x 也变成 6。
后缀:x++ 先取值后加
int x = 5; cout << x++ << endl; // 输出 5
x
5
x++ 的值
5
先取旧值,再加 1,x 变成 6。
练一练

x = 5 时,这三个输出是什么?

程序
int x = 5; cout << ++x << endl; cout << x++ << endl; cout << x << endl;
程序的输出是什么?
A6 6 7
B6 5 6
C6 6 6
D5 6 7
选 A:6 6 7 —— 第二行 x++ 先取值(6)再加,最后 x 是 7。
自增示例

链式自增:逐行跟踪 x 和 y 的值

程序
int x = 0, y = 0; x = ++y; // y 变 1,x=1 y = ++x; // x 变 2,y=2 x = y++; // x 取 2,y 变 3 y = x++; // y 取 2,x 变 3
语句xy说明
x = ++y11y 先加 1,x 取 1
y = ++x22x 先加 1,y 取 2
x = y++23x 取旧值 2,y 加 1
y = x++32y 取旧值 2,x 加 1
!
把每个表达式当成取值 + 变量变化两步,就不会写错。
C++ 自增与自减

复合赋值:x += 5 就是 x = x + 5

简写,读起来更快
x += 5; // x = x + 5 x -= 5; // x = x - 5 x++; // 等价于 x += 1 x--; // 等价于 x -= 1
+=
加法赋值
x += 5
-=
减法赋值
x -= 5
*=
乘法赋值
x *= 5
!
还有 /= 和 %=
x /= 5; // x = x / 5 x %= 5; // x = x % 5
C++ 自增与自减

字符也能自增:c++ 让字符走到下一个

字符按顺序向后走
char c = 'X'; c++; // c 变成 'Y' cout << c << endl; // 输出 Y c += 2; // 'Y' + 2 = '[' cout << c << endl; // 输出 [
运行窗口
Y [
下面的代码输出什么?
char c = 'X'; c++; // 第 1 行输出 c += 2; // 第 2 行输出
AY [
BY Z
CY A
DX Y
选 A:Y [ —— X 加 1 是 Y,Y 加 2 是 [。
C++ 自增与自减

优先级:++ 比算术高,+= 比算术低

++ 优先级高于算术
x = 5 + ++y; // 先 ++y,再 5 + y
+= 优先级低于算术
x += 5 + y; // 等价于 x = x + (5 + y)
!
复杂表达式 x = y++ + ++z 依赖运算顺序,容易出错——少用自增,或用括号明确顺序。
练一练:a=5, b=10,c = a++ + ++b,输出 a b c 是?
A6 11 17
B6 11 16
C5 11 16
D6 10 16
选 B:6 11 16 —— a++ 取 5(a 变 6),++b 得 11,c = 16。
02
PART 02 · 格式化输入输出篇

让程序精确控制输入输出

scanf 读入、printf 输出,格式符号决定数据的宽度和小数位。

scanf 输入 printf 输出 特殊格式 精度控制
C++ 格式化输入输出

scanf:带上 & 的格式化输入

按格式读入
int x, y; scanf("%d %d", &x, &y); cout << x << " " << y << endl;
运行窗口
输入:10 20 输出:10 20
&
每个变量前都要加 &,数据才能真存进变量,格式符号要和类型匹配。
最常用的 4 个
%d
整数
%f
浮点数
%c
字符
%s
字符串
延伸:%lld long long、%lf double、%x 十六进制
C++ 格式化输入输出

printf:不需要 & 的格式化输出

按格式输出
int x = 5, y = 10; printf("x = %d, y = %d\n", x, y);
运行窗口
x = 5, y = 10
x
和 scanf 不同:printf 不需要 &,直接写变量名。
常用格式符号
%d
int 整数
%f
float 浮点
%c
字符
%s
字符串
%lld
long long
%lf
double
%x
十六进制
%o
八进制
重点:%d %f %c %s 必须掌握。
C++ 格式化输入输出

特殊格式:宽度、对齐、补零、小数位

格式数值示例输出(_ 为空格)
%5d42___42
%-5d4242___
%05d4200042
%.2f3.141593.14
%8.2f3.14159____3.14
%
%md 中 m 是总宽度(右对齐),%-md 左对齐,%0md 用 0 补齐,%m.nf 总宽 m、保留 n 位小数。
练一练

输入 123 3.14 A,输出会是什么?

程序
int a; float b; char c; scanf("%d %f %c", &a, &b, &c); printf("a=%d, b=%.2f, c=%c\n", a, b, c);
运行窗口
输入:123 3.14 A a=123, b=3.14, c=A
程序的输出是什么?
Aa=123, b=3.14, c=A
Ba=123, b=3.14, c=
Ca=123, b=3.00, c=A
D编译错误
选 A:%.2f 保留两位小数,c 读到字符 A。
C++ 格式化输入输出

cout 精度:setprecision 与 fixed

需要 #include <iomanip>
#include <iomanip> double pi = 3.14159265358979; cout << setprecision(4) << pi << endl; cout << fixed << setprecision(2) << pi << endl; cout << fixed << setprecision(6) << pi << endl;
运行结果
3.142 3.14 3.141593
i
默认 setprecision 管有效数字,加上 fixed 后管小数点后位数
C++ 浮点数精度

float 与 double:第 7 位开始分家

程序
float f = 1.0 / 3.0; double d = 1.0 / 3.0; cout << fixed << setprecision(20); cout << "float: " << f << endl; cout << "double: " << d << endl;
运行结果
终端
float: 0.33333334326744079590 double: 0.33333333333333331483
i
float 约 7 位有效数字,double 约 15 位,高精度用 double。
C++ 浮点数精度

浮点比较:别用 ==,用 fabs 判差

错误:直接 ==
double a = 0.1 + 0.2; double b = 0.3; if (a == b) cout << "相等";
结果不一定相等:0.1+0.2 ≠ 0.3
正确:判断差是否足够小
double a = 0.1 + 0.2; double b = 0.3; if (fabs(a - b) < 1e-9) cout << "相等";
用 fabs(a-b) < 1e-9 判近似相等
!
浮点有精度限制,几乎不该直接 == 判断相等——改成判差值小于一个很小的数。
C++ 格式化输入输出

%0md:把日期和时间对齐整齐

代码
printf("%04d-%02d-%02d\n", 2023, 11, 5); printf("%02d:%02d:%02d\n", 15, 30, 25);
运行窗口
2023-11-05 15:30:25
%02d 的作用
%04d → 5 写成 "0005" %02d → 9 写成 "09"
i
%md 中 m 是总宽度,不足用 0 补(%0md),日期时间用 %04d-%02d-%02d 很整齐。
练一练

x = 12.3456789,两个输出都是什么?

程序
double x = 12.3456789; cout << fixed << setprecision(2) << x << endl; printf("%08.2f\n", x);
程序的输出是什么?
A12.35 00012.35
B12.35 0012.35
C12.35 012.35
D12.3456789 12.35
选 A:12.35(两位小数),%08.2f 总宽 8、补零得 00012.35。
03
PART 03 · 习题篇

综合挑战

用今天的知识,解两道关于浮点输出与百分号的题目。

浮点除法 保留小数 百分号 %%
习题讲解

两道浮点题:注意类型与格式

计算分数的浮点数值
double a, b; cin >> a >> b; printf("%.9f\n", b / a);
保留 9 位小数,用 double 存
输出保留 3 位小数的浮点数
float a; cin >> a; printf("%.3f\n", a);
注意:题目要求 float 类型
%
想输出百分号 %,要写 %%——因为 % 在格式串里是特殊字符。
小结

今天你学会了:

自增与自减
前缀 / 后缀取值 复合赋值 += 字符自增 优先级
格式化输入输出
scanf / & printf 特殊格式 %md cout 精度
浮点与习题
float / double fabs 比较 %0md 日期 百分号 %%
课后任务:OJ · J1 第四单元作业(100 分通过)。下一单元:循环结构(for 与 while)。
大卫信奥 · J1 知识点 · 五单元
05

习题课

综合运用前三单元知识——数据范围、格式化输出、除法与求余。

例题讲解 挑战题 · 分糖果
习题课封面
今日路线

三类内容,把前三单元的知识串起来

01
例题讲解
四舍五入、并联电阻、等差数列、浮点数求余。
02
挑战题
小朋友分糖果——一步步模拟过程。
03
小结
回顾知识点,完成课后练习。
01
PART 01 · 例题讲解

把四道例题讲透

格式化输出、浮点运算、数列计算、求余——逐个击破。

四舍五入 并联电阻 等差数列 浮点数求余
例题 1 · 浮点数四舍五入

printf("%.0f"):把小数四舍五入成整数

#include <bits/stdc++.h> using namespace std; int main() { double x; cin >> x; printf("%.0f\n", x); return 0; }
运行窗口
输入:3.6 输出:4 输入:3.4 输出:3
%
%.0f 表示保留 0 位小数——四舍五入到整数。
3.6
→ 4
3.4
→ 3
另一种方法:先加 0.5 再取整
long long y = (long long)(x + 0.5);
3.6 → 4.1 → 4  x+0.5 后取整
例题 2 · 计算并联电阻的阻值

R = 1 / (1/r1 + 1/r2):先倒数,再求和,再取倒数

两个电阻并联
r1
r2
R
R = 1 / (1/r1 + 1/r2)
先算倒数 → 加起来 → 再取倒数
#include <bits/stdc++.h> using namespace std; int main() { double r1, r2; cin >> r1 >> r2; double r = 1 / (1/r1 + 1/r2); printf("%.2f\n", r); return 0; }
输入:2 2 → 输出:1.00
1/(1/2+1/2)=1/(1)=1.00
例题 3 · 等差数列末项计算

先找公差 d,再用公式求第 n 项

公式卡片
an = a1 + (n − 1) × d
第 n 项 = 首项 + (项数 − 1) × 公差
d
公差 d = a2 − a1:相邻两项的差。
#include <bits/stdc++.h> using namespace std; int main() { int a1, a2, n; cin >> a1 >> a2 >> n; int d = a2 - a1; // 公差 int an = a1 + (n - 1) * d; // 末项 printf("%d\n", an); return 0; }
输入:2 5 4 → 输出:11
d=3,a4=2+3×3=11
例题 4 · 计算浮点数相除的余

浮点数没有 %,先把商拆出来再算余

#include <bits/stdc++.h> using namespace std; int main() { double a, b; cin >> a >> b; int k = a / b; // 整数部分 double r = a - k * b; // 计算余数 cout << r; return 0; }
输入:7.5 2 → 输出:1.5
kint
3
=
a / b 的整数部分
rdouble
1.5
=
a − k × b
%
整数 % 只对整数取余,
浮点数求余 = a − (a/b 整数部分) × b
02
PART 02 · 挑战题

小朋友分糖果

用变量和模拟,一步步还原一次分糖果的过程。

题意分析 编写模拟 运行验证
挑战题 · 小朋友分糖果

5 位小朋友围圆桌,依次把糖果分 3 份

1
2
3
4
5
把糖果均分成 3 份,有多余的,自己吃掉。
自己留 1 份
另外 2 份分给左、右两边邻居
1 号到 5 号 依次各做一次,正好一圈。
挑战题 · 编写模拟(一)

读入糖果,从 1 号开始轮流“分 3 份”

#include <bits/stdc++.h> // 通用头文件 using namespace std; int main() { int a, b, c, d, e; // 5 位小朋友的糖果 cin >> a >> b >> c >> d >> e; // 输入初始糖果 int t = 0; // t:吃掉的糖果总数 // 1 号:分 3 份,留 1 份,左右各 1 份 t = t + a % 3; // 多余的糖果吃掉 a = a / 3; b += a; e += a; // 留一份,给 b 和 e // 2 号 t = t + b % 3; // 多余的糖果吃掉 b = b / 3; a += b; c += b; // 留一份,给 a 和 c // 3 号 t = t + c % 3; // 多余的糖果吃掉 c = c / 3; b += c; d += c; // 留一份,给 b 和 d
挑战题 · 编写模拟(二)

接上一页:4、5 号再分,最后输出答案

// 4 号 t = t + d % 3; // 多余的糖果吃掉 d = d / 3; c += d; e += d; // 留一份,给 c 和 e // 5 号 t = t + e % 3; // 多余的糖果吃掉 e = e / 3; d += e; a += e; // 留一份,给 d 和 a // 输出答案 cout << a << ' ' << b << ' ' << c << ' ' << d << ' ' << e << endl; cout << t; // 吃掉的糖果总数 return 0; }
挑战题 · 运行验证

输入 10 10 10 10 10,一轮后变成了多少?

运行窗口
输入:10 10 10 10 10 输出:12 8 8 9 5 吃掉的糖果总数:8
!
模拟顺序:1→2→3→4→5,每个人分到的邻居糖果会叠加。
一轮结束后每人手里的糖果
a
12
b
8
c
8
d
9
e
5
t
吃掉的糖果总数 t = 8:1 号到 5 号吃掉的部分加起来。
03
PART 03 · 小结

这一节的关键

回顾今天用到的知识点,准备好课后练习。

精确输出 数据类型 求余 模拟
小结

今天你学会了:

格式化输出
printf("%.0f") printf("%.2f") printf("%d")
数据与运算
double 存小数 整数除法取整 % 取余 浮点数求余
模拟思维
按顺序模拟 边模拟边统计 拆成小步骤
课后任务:OJ · 本单元习题(100 分通过)。下一单元:更多数据类型与 if 分支。