- 第 194 篇 -
Date: 2026 - 03- 19 | 周四
Author: 郑龙浩(仟墨)
蓝桥云课中Lv.1难度中的绝大部分题
2026-03-19-算法刷题day27-难度Lv.1
我本以为Lv.1难度的所有题,除了涉及某些数学或者现实中的知识盲区的,都能做出来
没想到还是有的不是很好做,难点主要是「填空题」,要去理解写代码的人的思路,而不是自己从头构思思路,要去揣测他的想法,有的我就感觉理解起来有些困难,后面有个填空题用到了「三向切分」的思路,我就不会了,之前确实没写过这类似的代码
这个Lv.1的难度太虚了,编程题确实是Lv.1的难度,但是部分填空题,对于我来说不是Lv.1,虽然有的能蒙出来,但是整个代码我是不能理解的,且很多填空题不是纯基础题,就是个算法题
填空涉及到DP和回溯的,反正我都迷迷糊糊的,不是很明白,难受
最近还有其他比赛要搞,本来想今天把lv1和lv2的题都做一做,看来是做不完了,明天尽量做吧
文章目录
- 2026-03-19-算法刷题day27-难度Lv.1
-
- 1-蓝桥云课3499-幸运数字
- 2-蓝桥云课2379-英文字母
- 3-蓝桥云课2371-3的倍数
- 4-蓝桥云课2366-双阶乘
- 5-蓝桥云课2365-求余
- 6-蓝桥云课2364-浮点数
- 7-蓝桥云课2353-日期格式
- 8-蓝桥云课2118-排列字母
- 9-蓝桥云课2095-九进制转十进制
- 10-蓝桥云课1452-时间显示
- 11-蓝桥云课707-等额本金
- 12-蓝桥云课702-啤酒和饮料
- 13-蓝桥云课681-立方变自身
- 14-蓝桥云课605-年号字串
- 15-蓝桥云课592-门牌制作
- 16-蓝桥云课549-扫雷
- 17-蓝桥云课504-单词分析
- 18-蓝桥云课475-神秘的三位数
- 19-蓝桥云课468-身份证号校验
- 20-蓝桥云课467-干支纪年(没细读题,需要复习)
- 21-蓝桥云课456-三部排序(需要复习)
- 22-蓝桥云课436-九数组分数(需要复习)
- 23-蓝桥云课422-最大公共子串(需要复习)
1-蓝桥云课3499-幸运数字
### 问题描述
哈沙德数是指在某个固定的进位制当中,可以被各位数字之和整除的正整数。例如 126126 是十进制下的一个哈沙德数,因为 (126)10(1+2+6)=0(126)10mod(1+2+6)=0;126126 也是八进制下的哈沙德数,因为 (126)10=(176)8(126)10=(176)8 ,(126)10mod(1+7+6)=0(126)10mod(1+7+6)=0;同时 126126 也是 1616 进制下的哈沙德数,因为 (126)10=(7e)16(126)10=(7e)16 ,(126)10mod(7+e)=0(126)10mod(7+e)=0。小蓝认为,如果一个整数在二进制、八进制、十进制、十六进制下均为哈沙德数,那么这个数字就是幸运数字,第 11 至第 1010 个幸运数字的十进制表示为:1,2,4,6,8,40,48,72,120,126...1,2,4,6,8,40,48,72,120,126...。现在他想知道第 20232023 个幸运数字是多少?你只需要告诉小蓝这个整数的十进制表示即可。
答案提交
这是一道结果填空的题,你只需要算出结果后提交即可。本题的结果为一个整数,在提交答案时只填写这个整数,填写多余的内容将无法得分。
【思路】
纯模拟,没什么技巧
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 1-蓝桥云课3499-幸运数字
* 算法:
* Author:郑龙浩
* Date:2026-03-19
* 用时:
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
ll newNum(ll num, int m) {
ll ans = 0;
while (num) {
ans += num % m;
num /= m;
}
return ans;
}
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
int cnt = 0;
for (int i = 1;; i++) {
ll a, b, c, d;
a = i % newNum(i, 2);
b = i % newNum(i, 8);
c = i % newNum(i, 10);
d = i % newNum(i, 16);
if (a == 0 && b == 0 && c == 0 && d == 0) cnt++;
if (cnt == 2023) {
cout << i;
break;
}
}
return 0;
}
2-蓝桥云课2379-英文字母
### 问题描述
输入一个正整数 nn, 输出第 nn 个大写英文字母。
输入格式
输入一行包含一个正整数 nn 。
输出格式
输出一行包含一个字母。
样例输入 1
text
12
样例输出 1
text
L
样例输入 2
TEXT
17
样例输出 2
text
Q
评测用例规模与约定
对于所有评测用例, 1≤n≤261≤n≤26 。
运行限制
- 最大运行时间:1s
- 最大运行内存: 256M
【思路】
没什么技巧
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 2-蓝桥云课2379-英文字母
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
* 用时:2min
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
int n; cin >> n;
cout << (char)('A' + n - 1);
return 0;
}
3-蓝桥云课2371-3的倍数
### 问题描述
小蓝对 3 的倍数很感兴趣。现在他手头有三个不同的数 a,b,ca,b,c, 他想知道, 这三个数中是不是有两个数的和是 3 的倍数。
例如, 当 a=3,b=4,c=6a=3,b=4,c=6 时, 可以找到 aa 和 cc 的和是 3 的倍数。 例如, 当 a=3,b=4,c=7a=3,b=4,c=7 时, 没办法找到两个数的和是 3 的倍数。
输入格式
输入三行, 每行一个整数, 分别表示 a,b,ca,b,c 。
输出格式
如果可以找到两个数的和是 3 的倍数, 输出 yes, 否则输出 no。
样例输入 1
text
3
4
6
样例输出 1
text
yes
样例输入 2
text
3
4
7
样例输出 2
text
no
评测用例规模与约定
对于所有评测用例,1≤a≤b≤c≤1001≤a≤b≤c≤100。
【思路】
没有技巧
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 3-蓝桥云课2371-3的倍数
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
* 用时:3min
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
int a, b, c;
cin >> a >> b >> c;
int n1 = a + b, n2 = b + c, n3 = a + c;
n1 %= 3; n2 %= 3; n3 %= 3;
if (n1 == 0 || n2 == 0 || n3 == 0) cout << "yes";
else cout << "no";
return 0;
}
4-蓝桥云课2366-双阶乘
问题描述
一个正整数的双阶乘, 表示不超过这个正整数且与它有相同奇偶性的所有 正整数乘积。 nn 的双阶乘用 n!!n!! 表示。
例如:
3!!=3×1=38!!=8×6×4×2=38411!!=11×9×7×5×3×1=103953!!=3×1=38!!=8×6×4×2=38411!!=11×9×7×5×3×1=10395
请问, 2021!!2021!! 的最后 5 位 (这里指十进制位) 是多少?
注意: 2021!!=2021×2019×⋯×5×3×12021!!=2021×2019×⋯×5×3×1 。
提示: 建议使用计算机编程解决问题。
答案提交
这是一道结果填空的题,你只需要算出结果后提交即可。本题的结果为一 个整数, 在提交答案时只填写这个整数, 填写多余的内容将无法得分。
运行限制
- 最大运行时间:1s
- 最大运行内存: 256M
【思路】
题目要求"最后5位",即取结果的后5位数。
-
在乘法过程中,**更高位(第6位及之后)** 会不断累积
-
但更高位不影响最终的后5位结果
-
每次乘完立即
% 100000,相当于只保留后5位,丢弃更高位 -
这样做可以防止数值溢出,且不影响最终答案
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 4-蓝桥云课2366-双阶乘
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
* 用时:5min
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
ll ans = 1;
for (ll i = 2021; i >= 1; i -= 2) {
ans = ans * i % 100000;
}
cout << ans % 100000;
return 0;
}
5-蓝桥云课2365-求余
【题目】
在 C/C++/Java/Python 等语言中, 使用 % 表示求余, 请问 2021 % 20 的值是多少?
【代码】
cpp
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
cout << 2021 % 20;
return 0;
}
6-蓝桥云课2364-浮点数
【题目】
IEEE 754 规定一个双精度浮点数百 1 位符号位、11 位阶和 52 位尾数组成 (以上位数都表示二进制位数)。
请问,按此规定一个双精度浮点数占用几个字节?
【思路】
刚开始确实没反应过来,这是一个「位」转「字节」的题
算出「总位数」/ 「8位」,因为8位是1字节
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 6-蓝桥云课2364-浮点数
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
* 用时:2min
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
cout << (1 + 11 + 52) / 8;
return 0;
}
7-蓝桥云课2353-日期格式
问题描述
小蓝要处理非常多的数据, 其中有一些数据是日期。
在小蓝处理的日期中有两种常用的形式: 英文形式和数字形式。
英文形式采用每个月的英文的前三个宁母作为月份标识, 后面跟两位数字 表示日期, 月份标识第一个字母大写, 后两个字母小写, 日期小于 10 时要补 前导 0s 1 月到 12 月英文的前三个字母分别是 Jan、Feb、Mar、Apr、May、 Jun、Jul、Aug、Sep、Oct、Nov、Dec:
数字形式直接用两个整数表达, 中间用一个空格分隔, 两个整数都不写前导 0。其中月份用 1 至 12 分别表示 1 月到 12 月。
输入一个日期的数字形式, 请输出它的英文形式。
输入格式
输入一行包含两个整数, 分别表示日期的月和日。
输出格式
输出对应的英文形式:
样例输入
text
2 8
样例输出
text
Feb08
样例输入
text
10 18
样例输出
text
Oct18
【思路】
简单题,但是有个注意的点,我刚开始没注意,就是输出的时候日要有「前导0」
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 7-蓝桥云课2353-日期格式
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
string nums[12] = {"Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"};
int a, b; cin >> a >> b;
cout << nums[a - 1];printf("%02d", b);
return 0;
}
8-蓝桥云课2118-排列字母
【题目】
本题为填空题,只需要算出结果后,在代码中使用输出语句将所填结果输出即可。
小蓝要把一个字符串中的字母按其在字母表中的顺序排列。
例如,LANQIAO 排列后为 AAILNOQ。
又如,GOODGOODSTUDYDAYDAYUP 排列后为 AADDDDDGGOOOOPSTUUYYY。
请问对于以下字符串,排列之后字符串是什么?
WHERETHEREISAWILLTHEREISAWAY
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 8-蓝桥云课2118-排列字母
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
string s; cin >> s;
sort(s.begin(), s.end());
cout << s;
return 0;
}
9-蓝桥云课2095-九进制转十进制
【题目】
本题为填空题,只需要算出结果后,在代码中使用输出语句将所填结果输出即可。
九进制正整数 (2022)9转换成十进制等于多少?
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 9-蓝桥云课2095-九进制转十进制
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
int result = 0;
int num = 2022;
int i = 0;
while (num) {
result += (num % 10) * pow(9, i);
num /= 10;
i++;
}
cout << result;
return 0;
}
10-蓝桥云课1452-时间显示
题目描述
小蓝要和朋友合作开发一个时间显示的网站。
在服务器上,朋友已经获取了当前的时间,用一个整数表示,值为从 19701970 年 11 月 11 日 00:00:0000:00:00 到当前时刻经过的毫秒数。
现在,小蓝要在客户端显示出这个时间。小蓝不用显示出年月日,只需要显示出时分秒即可,毫秒也不用显示,直接舍去即可。
给定一个用整数表示的时间,请将这个时间对应的时分秒输出。
输入描述
输入一行包含一个整数,表示时间。
输出描述
输出时分秒表示的当前时间,格式形如 HH:MM:SS,其中 HH 表示时,值为 00 到 2323,MM 表示分,值为 00 到 5959,SS 表示秒,值为 00 到 5959。时、分、秒 不足两位时补前导 00。
输入输出样例
示例 1
输入
txt
46800999
输出
txt
13:00:00
示例 2
输入
txt
1618708103123
输出
txt
01:08:23
评测用例规模与约定
对于所有评测用例,给定的时间为不超过 10181018 的正整数。
【思路】
注意的点
题目给出的输入是「毫秒数」,不是「秒数」
第一次我根据秒数写的,怎么都不对,才发现题目写的是毫秒
然后就出现了一个挺尴尬的事情,我TM不知道一秒是多少毫秒,呃呃呃,我刚开始按照1秒是100毫秒去算的,答案不对
然后才知道一秒是1000毫秒,这次可给我记住了
然后就是将最后总毫秒数 / 1000,得出秒数
- 今天总秒数/每小时的秒数得出 到现在的小时数
- 今天总秒数%每小时秒数得出 不满足1h的剩余秒数
- 剩余秒数 / 每分钟的秒数,得出现在的分钟数
- 最后直接将今天总秒数%每分钟秒数,得出最后的秒数
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 10-蓝桥云课1454-时间显示
* 需要复习,计算出错
* Author:郑龙浩
* Date:2026-03-19
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
ll n; cin >> n;
n = n % (24 * 60 * 60 * 1000); // 取余得到一天内的剩余毫秒数
n /= 1000; // 毫秒转换为秒
int h, m, s;
h = n / 3600; // 总秒数 / 每小时的秒数 --> 小时数
m = n % 3600 / 60; // 总秒数 % 每小时秒数 --> 剩余秒数
// 剩余秒数 / 60 --> 分钟数
s = n % 60; // 总秒数 % 每分钟秒数 --> 秒数
printf("%02d:%02d:%02d", h, m, s);
return 0;
}
11-蓝桥云课707-等额本金
【题目】
本题为填空题,只需要算出结果后,在代码中使用输出语句将所填结果输出即可。
小明从银行贷款 33 万元。约定分 2424 个月,以等额本金方式还款。
这种还款方式就是把贷款额度等分到 2424 个月。每个月除了要还固定的本金外,还要还贷款余额在一个月中产生的利息。
假设月利率是:0.0050.005,即:千分之五。
第一个月,小明要还本金 12501250, 还要还利息:30000∗0.00530000∗0.005,总计 1400.001400.00。
第二个月,本金仍然要还 12501250, 但利息为:(30000−1250)∗0.005(30000−1250)∗0.005 总计 1393.751393.75。
请问:小明在第 1515 个月,应该还款多少(本金和利息的总和)?
请把答案金额四舍五入后,保留两位小数。注意:32.532.5,一定要写为:32.5032.50。
【思路】
注意输出的不是利息,而是本+利即可
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 11-蓝桥云课707-等额本金
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
* 用时:4min
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
printf("%.02f", 1250 + (30000 - 1250 * 14) * 0.005);
return 0;
}
12-蓝桥云课702-啤酒和饮料
【题目】
本题为填空题,只需要算出结果后,在代码中使用输出语句将所填结果输出即可。
啤酒每罐 2.32.3 元,饮料每罐 1.91.9 元。小明买了若干啤酒和饮料,一共花了 82.382.3 元。
我们还知道他买的啤酒比饮料的数量少,请你计算他买了几罐啤酒。
【思路】
首先算出nm,表示82.3最多买多少啤酒,多少饮料
需要注意:饮料数量 > 啤酒数量
所以在写循环的时候,啤酒的数量是从饮料数量 + 1 开始遍历的
然后计算出 两者购买时总费用是否为82.3即可
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 12-蓝桥云课702-啤酒和饮料
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
* 用时:3 min 56 s
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
int n = 82.3 / 2.3;
int m = 82.3 / 1.9;
for (int i = 0; i < n; i++) {
for (int j = i + 1; j < m; j++) {
if (i * 2.3 + j * 1.9 == 82.3) {
cout << i;
break;
}
}
}
return 0;
}
13-蓝桥云课681-立方变自身
【题目】
本题为填空题,只需要算出结果后,在代码中使用输出语句将所填结果输出即可。
观察下面的现象,某个数字的立方,按位累加仍然等于自身。
txt
1^3 = 1
8^3 = 512 5+1+2=8
17^3 = 4913 4+9+1+3=17
...
请你计算包括 1,8,171,8,17 在内,符合这个性质的正整数一共有多少个?
【思路】
错误1:
刚开始我将题目中的ii,当做了C++中的运算了,没注意题目指的是「立方」,所以刚开始费了点时间,写错了
后来改为 i *i * i就对了
错2:
我刚开始写的时候直接把循环写成了 < INT_MAX
但是运行起来会非常的慢,但是题目直接问 请你计算包括 1,8,171,8,17 在内,符合这个性质的正整数一共有多少个?
并没有说比如1000以内 1000以内的数
所以我断定只有前100或前1000或前10000等有符合这个条件的数字,否则题目会给出范围的
然后我就将for从100到10000尝试,发现从1000开始,无论数字改为多少,答案都是只有6个,所以,我就试了一下是否正确,直接对了
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 13-蓝桥云课681-立方变自身
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
* 用时:10min
* 原因是:刚开始我将题目中的i^i,当做了C++中的^运算了,没注意题目指的是「立方」,所以刚开始费了点时间,写错了
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
int cnt = 0;
for (int i = 1; i < 10000; i++) {
int sum = 0;
int n2 = i * i * i;
while (n2) {
sum += n2 % 10;
n2 /= 10;
}
if (i == sum) cnt++;
}
cout << cnt;
return 0;
}
14-蓝桥云课605-年号字串
【题目】
本题为填空题,只需要算出结果后,在代码中使用输出语句将所填结果输出即可。
小明用字母 AA 对应数字 11,BB 对应 22,以此类推,用 ZZ 对应 2626。对于 2727 以上的数字,小明用两位或更长位的字符串来对应,例如 AAAA 对应 2727,ABAB 对应 2828,AZAZ 对应 5252,LQLQ 对应 329329。
请问 20192019 对应的字符串是什么?
【思路】
这就是个进制转换的问题,就是计算如何将26进制的数字加起来
我第一次看到并不知道是进制题,所以模拟了一下脑海中的想法:cout << ('L' - 'A' + 1) * 26 + 'Q' - 'A' + 1;,看一下是否等于题目中的329,发现还真是,我就断定是这样了
且进位用的也是26位数,所以进位不能* 10,而是* 26
刚开始我用了两层for,发现不够,然后又加了一层
但是这里要注意,i 表示的是最高位,即百位
- 十进制的时候,表示百位,要
i * 10 * 10 - 26进制的时候,表示百位,要
i * 26 * 26
所以刚开始,我写的时候,写错了写成了i * 26 * 10,然后我想了想,根据十进制的做法是乘两个十,那么26进制不就是乘两个26吗
然后就做出来了
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 14-蓝桥云课605-年号字串
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
* 用时:9min 08s
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
// cout << ('L' - 'A' + 1) * 26 + 'Q' - 'A' + 1;
for (char i = 'A'; i <= 'Z'; i++) {
for (char j = 'A'; j <= 'Z'; j++) {
for (char k = 'A'; k <= 'Z'; k++) {
if ((i - 'A' + 1) * 26 * 26 + (j - 'A' + 1) * 26 + k - 'A' + 1 == 2019) {
cout << i << j << k;
return 0;
}
}
}
}
return 0;
}
15-蓝桥云课592-门牌制作
【题目】
本题为填空题,只需要算出结果后,在代码中使用输出语句将所填结果输出即可。
小蓝要为一条街的住户制作门牌号。
这条街一共有 20202020 位住户,门牌号从 11 到 20202020 编号。
小蓝制作门牌的方法是先制作 00 到 99 这几个数字字符,最后根据需要将字符粘贴到门牌上,例如门牌 1017 需要依次粘贴字符 1、0、1、71、0、1、7,即需要 11 个字符 00,22 个字符 11,11 个字符 77。
请问要制作所有的 11 到 20202020 号门牌,总共需要多少个字符 22?
【思路】
本想用数学直接计算出结果,发现想错了,反而多耗时了4min,暴力反而只用了1 min多点写出来了,下次遇到这种题,如果无法直接算出来,还是选择暴力更节省时间
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 15-蓝桥云课592-门牌制作
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
* 本想用数学直接计算出结果,发现想错了,反而多耗时了4min,暴力反而只用了1 min多点写出来了,下次遇到这种题,如果无法直接算出来,还是选择暴力更节省时间
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
// cout << 1 + (2 * 10) + (20 * 10 + 1) + (202 * 10); // 用了四分钟,没想出来直接算该咋算
// 用时:1min 41s
int cnt = 0;
for (int i = 1; i <= 2020; i++) {
int n = i;
while (n) {
if (n % 10 == 2) cnt++;
n /= 10;
}
}
cout << cnt;
return 0;
}
16-蓝桥云课549-扫雷
题目描述
在一个 nn 行 mm 列的方格图上有一些位置有地雷,另外一些位置为空。
请为每个空位置标一个整数,表示周围八个相邻的方格中有多少个地雷。
输入描述
输入的第一行包含两个整数 n,mn,m。
第 22 行到第 n+1n+1 行每行包含 mm 个整数,相邻整数之间用一个空格分隔。如果对应的整数为 00,表示这一格没有地雷。如果对应的整数为 11,表示这一格有地雷。
其中,1≤n,m≤1001≤n,m≤100 分钟后还是在当天。
输出描述
输出 nn 行,每行 mm 个整数,相邻整数之间用空格分隔。
对于没有地雷的方格,输出这格周围的地雷数量。对于有地雷的方格,输出 99。
输入输出样例
示例 1
输入
txt
3 4
0 1 0 0
1 0 1 0
0 0 1 0
输出
txt
2 9 2 1
9 4 9 2
1 3 9 2
【思路】
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 16-蓝桥云课549-扫雷
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
* 用时:12 min 20 s
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int direction[8][2] = {{1, 0}, {0, 1}, {-1, 0}, {0, -1}, {1, -1}, {1, 1}, {-1, 1}, {-1, -1}};
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
int n, m; cin >> n >> m;
vector <vector <int>> nums(n, vector <int> (m, 0));
for (int i = 0; i < n; i++) {
for (int j = 0; j < m; j++) {
cin >> nums[i][j];
}
}
vector <vector <int>> results(n, vector <int> (m, 0));
for (int i = 0; i < n; i++) {
for (int j = 0; j < m; j++) {
if (nums[i][j] == 1) {results[i][j] = 9; continue;}
for (int x = 0; x < 8; x++) {
int nextX = i + direction[x][0];
int nextY = j + direction[x][1];
if (nextX >= 0 && nextX < n && nextY >= 0 && nextY < m)
if (nums[nextX][nextY] == 1) results[i][j] ++;
}
}
}
for (auto i: results) {
for (int j : i) cout << j << ' ';
cout << '\n';
}
return 0;
}
17-蓝桥云课504-单词分析
题目描述
小蓝正在学习一门神奇的语言,这门语言中的单词都是由小写英文字母组 成,有些单词很长,远远超过正常英文单词的长度。小蓝学了很长时间也记不住一些单词,他准备不再完全记忆这些单词,而是根据单词中哪个字母出现得最多来分辨单词。
现在,请你帮助小蓝,给了一个单词后,帮助他找到出现最多的字母和这 个字母出现的次数。
输入描述
输入一行包含一个单词,单词只由小写英文字母组成。
对于所有的评测用例,输入的单词长度不超过 1000。
输出描述
输出两行,第一行包含一个英文字母,表示单词中出现得最多的字母是哪 个。如果有多个字母出现的次数相等,输出字典序最小的那个。
第二行包含一个整数,表示出现得最多的那个字母在单词中出现的次数。
输入输出样例
示例 1
输入
txt
lanqiao
输出
txt
a
2
示例 2
输入
txt
longlonglongistoolong
输出
txt
o
6
【思路】
记得在输出字符的时候要转换为char,因为Max + 'a',按照转换规则,会转换为字节大的int而不是字节小的char
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 17-蓝桥云课504-单词分析
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
* 用时:5min
* 记得在输出字符的时候要转换为char,因为Max + 'a',按照转换规则,会转换为字节大的int而不是字节小的char
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
int main() {
ios::sync_with_stdio(0);
cin.tie(0); cout.tie(0);
string s; cin >> s;
int cnt[26] = {0};
for (char ch : s) {
cnt[ch - 'a']++;
}
int Max = 0;
for (int i = 0; i < 26; i++) {
if (cnt[i] > cnt[Max]) Max = i;
}
cout << (char)(Max + 'a') << '\n' << cnt[Max];
return 0;
}
18-蓝桥云课475-神秘的三位数
题目描述
本题为代码补全填空题,请将题目中给出的源代码补全,并复制到右侧代码框中,选择对应的编译语言(C/Java)后进行提交。若题目中给出的源代码语言不唯一,则只需选择其一进行补全提交即可。复制后需将源代码中填空部分的下划线删掉,填上你的答案。提交后若未能通过,除考虑填空部分出错外,还需注意是否因在复制后有改动非填空部分产生错误。
有这样一个3位数,组成它的3个数字阶乘之和正好等于它本身。即:abc = a! + b! + c!
下面的程序用于搜索这样的3位数。
请仔细阅读代码,并填写划线部分缺失的代码。
源代码
C
c
#include <stdio.h>
#include <stdlib.h>
int main()
{
int JC[] = {1,1,2,6,24,120,720,5040,40320,362880};
int i;
for(i=100; i<1000; i++)
{
int sum = 0;
int x = i;
while(__________)
{
sum += JC[x%10];
x /= 10;
}
if(i==sum) printf("%d\n", i);
}
return 0;
}
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 18-蓝桥云课475-神秘的三位数
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
* 用时:1 min
* 直接填就OK了
*/
#include <stdio.h>
#include <stdlib.h>
int main()
{
int JC[] = {1,1,2,6,24,120,720,5040,40320,362880};
int i;
for(i=100; i<1000; i++)
{
int sum = 0;
int x = i;
while(x)
{
sum += JC[x%10];
x /= 10;
}
if(i==sum) printf("%d\n", i);
}
return 0;
}
19-蓝桥云课468-身份证号校验
本题为代码补全填空题,请将题目中给出的源代码补全,并复制到右侧代码框中,选择对应的编译语言(C/Java)后进行提交。若题目中给出的源代码语言不唯一,则只需选择其一进行补全提交即可。复制后需将源代码中填空部分的下划线删掉,填上你的答案。提交后若未能通过,除考虑填空部分出错外,还需注意是否因在复制后有改动非填空部分产生错误。
如果让你设计个程序,用什么变量保存身份证号码呢?长整数可以吗?不可以!
因为有人的身份证最后一位是 "X"。
实际上,除了最后一位的 X,不会出现其它字母!
身份证号码 18 位 = 17 位 + 校验码
校验码的计算过程:
例如:身份证前 17 位 = ABCDEFGHIJKLMNOPQ
A~Q 每位数字乘以权值求和(每位数字和它对应的"权"相乘后累加)。
17 位对应的权值分别是:
7 9 10 5 8 4 2 1 6 3 7 9 10 5 8 4 2
求出的总和再对 11 求模
然后按下表映射:
余数: 0 1 2 3 4 5 6 7 8 9 10
校验码: 1 0 X 9 8 7 6 5 4 3 2
下面的代码实现了校验过程,输入串为身份证前17位,打印出校验码。
请仔细阅读代码,并填写划线部分缺失的代码。
源代码
C
c
#include <stdio.h>
#include <stdlib.h>
char verifyCode(char* s)
{
static int weight[] = {7,9,10,5,8,4,2,1,6,3,7,9,10,5,8,4,2};
static char map[] = {'1','0','X','9','8','7','6','5','4','3','2'};
int sum = 0;
for(int i=0; i<17; i++)
{
sum += (______________) * weight[i]; // 填空
}
return map[______________]; // 填空
}
int main(int argc, char* argv[])
{
printf("%c\n", verifyCode("32011119610215381"));
printf("%c\n", verifyCode("42900819801018236"));
return 0;
}
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 19-蓝桥云课468-身份证号校验
* 算法:没算法
* Author:郑龙浩
* Date:2026-03-19
* 填空题 用时:4min
*/
#include <stdio.h>
#include <stdlib.h>
char verifyCode(char* s)
{
static int weight[] = {7,9,10,5,8,4,2,1,6,3,7,9,10,5,8,4,2};
static char map[] = {'1','0','X','9','8','7','6','5','4','3','2'};
int sum = 0;
for(int i=0; i<17; i++)
{
sum += (s[i] - '0') * weight[i]; // 填空
}
return map[sum % 11]; // 填空
}
int main(int argc, char* argv[])
{
printf("%c\n", verifyCode("32011119610215381"));
printf("%c\n", verifyCode("42900819801018236"));
return 0;
}
20-蓝桥云课467-干支纪年(没细读题,需要复习)
本题为代码补全填空题,请将题目中给出的源代码补全,并复制到右侧代码框中,选择对应的编译语言(C/Java)后进行提交。若题目中给出的源代码语言不唯一,则只需选择其一进行补全提交即可。复制后需将源代码中填空部分的下划线删掉,填上你的答案。提交后若未能通过,除考虑填空部分出错外,还需注意是否因在复制后有改动非填空部分产生错误。
在我国古代和近代,一直采用干支法纪年。它采用 10 天干和 12 地支配合,一个循环周期为 60 年。
10 天干是:甲,乙,丙,丁,戊,己,庚,辛,壬,癸;
12 地支是:子,丑,寅,卯,辰,巳,午,未,申,酉,戌,亥。
如果某年是甲子,下一年就是乙丑,再下是丙寅,...癸酉,甲戌,乙亥,丙子,...
总之天干、地址都是循环使用,两两配对。
今年(2012)是壬辰年,1911 年辛亥革命
下面的代码根据公历年份输出相应的干支法纪年。已知最近的甲子年是1984 年。
请仔细阅读代码,并填写划线部分缺失的代码。
源代码
C
c
#include <stdio.h>
#include <stdlib.h>
void f(int year)
{
char* x[] = {"甲","乙","丙","丁","戊","己","庚","辛","壬","癸"};
char* y[] = {"子","丑","寅","卯","辰","巳","午","未","申","酉","戌","亥"};
int n = year - 1984;
while(n<0) n += 60;
printf("%s%s\n", x[_______], y[_______]);
}
int main(int argc, char* argv[])
{
f(1911);
f(1970);
f(2012);
return 0;
}
【思路】
这是一个双周期循环问题:
- 以1984年(甲子年)为基准,计算目标年份的偏移年数
n - 天干10年一循环,用
n % 10确定天干位置 - 地支12年一循环,用
n % 12确定地支位置 - 60是10和12的最小公倍数,形成一个完整的甲子循环
- 取模运算得到的是"在循环中的位置",而不是循环的圈数
我刚开始想的是都填n % 12,但是x数组会越界
后来我发现我理解错了
我起初理解的天干地支计算方式为 :
地支走到底,从头来的时候,天干就走一下,以此类推
所以之前我还纳闷,为什么60而不是120,哈哈哈,题目没仔细看
其实是 :
天干和地支共同往后走
还是没仔细读题
【代码】
21-蓝桥云课456-三部排序(需要复习)
三向切分
题目描述
本题为代码补全填空题,请将题目中给出的源代码补全,并复制到右侧代码框中,选择对应的编译语言(C/Java)后进行提交。若题目中给出的源代码语言不唯一,则只需选择其一进行补全提交即可。复制后需将源代码中填空部分的下划线删掉,填上你的答案。提交后若未能通过,除考虑填空部分出错外,还需注意是否因在复制后有改动非填空部分产生错误。
一般的排序有许多经典算法,如快速排序、希尔排序等。
但实际应用时,经常会或多或少有一些特殊的要求。我们没必要套用那些经典算法,可以根据实际情况建立更好的解法。
比如,对一个整型数组中的数字进行分类排序:
使得负数都靠左端,正数都靠右端,0 在中部。注意问题的特点是:负数区域和正数区域内并不要求有序。可以利用这个特点通过 1 次线性扫描就结束战斗!!
以下的程序实现了该目标。
其中 xx 指向待排序的整型数组,lenlen 是数组的长度。
请分析代码逻辑,并推测划线处的代码。
源代码
C
c
#include <stdio.h>
void show(int* x, int len)
{
int i;
for(i=0; i<len; i++)
{
printf("%d,",x[i]);
}
printf("\n");
}
void sort3p(int* x, int len)
{
int p = 0;
int left = 0;
int right = len-1;
while(p<=right){
if(x[p]<0){
int t = x[left];
x[left] = x[p];
x[p] = t;
left++;
p++;
}
else if(x[p]>0){
int t = x[right];
x[right] = x[p];
x[p] = t;
right--;
//p++;
}
else{
_______________;
}
}
show(x, len);
}
int main()
{
int a[] = {-1,0,1,-2,0,2,-3,0,0,3,-4,-5,4,-6,0,5,6};
int b[] = {-1,0,-1,-2,0,-2,-3,0,0,-3,-4,-5,-4,-6,0,-5,-6};
int c[] = {1,0,1,2,0,2,3,0,0,3,4,5,4,6,0,5,6};
sort3p(a,sizeof(a)/sizeof(int));
sort3p(b,sizeof(b)/sizeof(int));
sort3p(c,sizeof(c)/sizeof(int));
return 0;
}
【思路】
没做出来,不会做,我没想明白这个代码到底是什么意思
【AI解答】
算法:荷兰国旗三向切分算法
思路:
三个指针划分三个区域:
-
left左侧:已处理负数 -
left到p-1:已处理0 -
p到right:未处理区域 -
right右侧:已处理正数
处理规则:
-
遇到负数:与
left交换,left++和p++ -
遇到0:
p++ -
遇到正数:与
right交换,right--
为何负数交换后p++:
因为left到p-1区间内全是0 (循环不变式),交换后p指向0,而0已在正确位置,可直接跳过。
我的疑惑 :为什么left ~ p - 1都是0
因为在p是0的时候,p++,所以这就导致了left ~ p-1之间的所有元素都是0,所以当x[p]是负数的时候,x与left交换,其实是将元素0交换到了p的位置,所以p++直接跳到
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 10-蓝桥云课1454-时间显示
* 算法:三向切分
* Author:郑龙浩
* Date:2026-03-19
* 用时:10min
*/
#include <stdio.h>
void show(int* x, int len)
{
int i;
for(i=0; i<len; i++)
{
printf("%d,",x[i]);
}
printf("\n");
}
void sort3p(int* x, int len)
{
int p = 0; // 当前遍历指针
int left = 0; // 负数区右边界,left左侧全是负数
int right = len-1; // 正数区左边界,right右侧全是正数
while(p<=right){
if(x[p]<0){ // 当前是负数,放到负数区
int t = x[left];
x[left] = x[p];
x[p] = t;
left++;
p++; // 因为lefr ~ p - 1之间的数字都是0,所以将left交换到p后,p位置就是0了,直接跳过即可
}
else if(x[p]>0){ // 当前是正数,放到正数区
int t = x[right];
x[right] = x[p];
x[p] = t;
right--; // 交换后p的位置是之前没遇过的,也不知道是不是0,所以要处理的
}
else{ // 当前是0,直接跳过,让left ~ p-1之间保持都是0
p++;
}
}
show(x, len);
}
int main()
{
int a[] = {-1,0,1,-2,0,2,-3,0,0,3,-4,-5,4,-6,0,5,6};
int b[] = {-1,0,-1,-2,0,-2,-3,0,0,-3,-4,-5,-4,-6,0,-5,-6};
int c[] = {1,0,1,2,0,2,3,0,0,3,4,5,4,6,0,5,6};
sort3p(a,sizeof(a)/sizeof(int));
sort3p(b,sizeof(b)/sizeof(int));
sort3p(c,sizeof(c)/sizeof(int));
return 0;
}
22-蓝桥云课436-九数组分数(需要复习)
题目描述
本题为代码补全填空题,请将题目中给出的源代码补全,并复制到右侧代码框中,选择对应的编译语言(C/Java)后进行提交。若题目中给出的源代码语言不唯一,则只需选择其一进行补全提交即可。复制后需将源代码中填空部分的下划线删掉,填上你的答案。提交后若未能通过,除考虑填空部分出错外,还需注意是否因在复制后有改动非填空部分产生错误。
1,2,3...9 这九个数字组成一个分数,其值恰好为1/3,如何组法?
下面的程序实现了该功能,请填写划线部分缺失的代码。
源代码
C
c
#include <stdio.h>
void test(int x[])
{
int a = x[0]*1000 + x[1]*100 + x[2]*10 + x[3];
int b = x[4]*10000 + x[5]*1000 + x[6]*100 + x[7]*10 + x[8];
if(a*3==b) printf("%d/%d\n", a, b);
}
void f(int x[], int k)
{
int i,t;
if(k>=9){
test(x);
return;
}
for(i=k; i<9; i++){
{t=x[k]; x[k]=x[i]; x[i]=t;}
f(x,k+1);
_________________
}
}
int main()
{
int x[] = {1,2,3,4,5,6,7,8,9};
f(x,0);
return 0;
}
【思路】
这是个回溯算法,当前位置更换后,后面元素全部尝试完后,要再换回来,避免数组顺序出错
对于回溯,我依然没有很理解,这个一直是我心里的一个很大坎,然后因为回溯不理解,DP的很多题也不理解,哎,难受
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 22-蓝桥云课436-九数组分数
* 算法:回溯算法
* Author:郑龙浩
* Date:2026-03-19
* 用时:4min
*/
#include <stdio.h>
void test(int x[])
{
int a = x[0]*1000 + x[1]*100 + x[2]*10 + x[3];
int b = x[4]*10000 + x[5]*1000 + x[6]*100 + x[7]*10 + x[8];
if(a*3==b) printf("%d/%d\n", a, b);
}
void f(int x[], int k)
{
int i,t;
if(k>=9){
test(x);
return;
}
for(i=k; i<9; i++){
{t=x[k]; x[k]=x[i]; x[i]=t;}
f(x,k+1);
t=x[k]; x[k]=x[i]; x[i]=t; // 回溯
}
}
int main()
{
int x[] = {1,2,3,4,5,6,7,8,9};
f(x,0);
return 0;
}
23-蓝桥云课422-最大公共子串(需要复习)
题目描述
本题为代码补全填空题,请将题目中给出的源代码补全,并复制到右侧代码框中,选择对应的编译语言(C/Java)后进行提交。若题目中给出的源代码语言不唯一,则只需选择其一进行补全提交即可。复制后需将源代码中填空部分的下划线删掉,填上你的答案。提交后若未能通过,除考虑填空部分出错外,还需注意是否因在复制后有改动非填空部分产生错误。
最大公共子串长度问题就是: 求两个串的所有子串中能够匹配上的最大长度是多少。
比如:"abcdkkk" 和 "baabcdadabc", 可以找到的最长的公共子串是"abcd",所以最大公共子串长度为 4。
下面的程序是采用矩阵法进行求解的,这对串的规模不大的情况还是比较有效的解法。
请分析该解法的思路,并补全划线部分缺失的代码。
源代码
C
c
#include <stdio.h>
#include <string.h>
#define N 256
int f(const char* s1, const char* s2)
{
int a[N][N];
int len1 = strlen(s1);
int len2 = strlen(s2);
int i,j;
memset(a,0,sizeof(int)*N*N);
int max = 0;
for(i=1; i<=len1; i++){
for(j=1; j<=len2; j++){
if(s1[i-1]==s2[j-1]) {
a[i][j] = __________________________;
if(a[i][j] > max) max = a[i][j];
}
}
}
return max;
}
int main()
{
printf("%d\n", f("abcdkkk", "baabcdadabc"));
printf("%d\n", f("aaakkkabababa", "baabababcdadabc"));
printf("%d\n", f("abccbaacbcca", "ccccbbbbbaaaa"));
printf("%d\n", f("abcd", "xyz"));
printf("%d\n", f("ab", "ab"));
return 0;
}
【思路】
DP 算法
dp[i][j]表示:以字符串 s1 的第 i-1 个字符结尾,同时以字符串 s2 的第 j-1 个字符结尾的最长公共子串的长度。
【代码】
cpp
/* 2026-03-19-算法打卡day27
* 23-蓝桥云课422-最大公共子串
* 算法:动态规划
* Author:郑龙浩
* Date:2026-03-19
*/
#include "bits/stdc++.h"
using namespace std;
typedef long long ll;
#include <stdio.h>
#include <string.h>
#define N 256
int f(const char* s1, const char* s2)
{
int a[N][N];
int len1 = strlen(s1);
int len2 = strlen(s2);
int i,j;
memset(a,0,sizeof(int)*N*N);
int max = 0;
for(i=1; i<=len1; i++){
for(j=1; j<=len2; j++){
if(s1[i-1]==s2[j-1]) {
a[i][j] = a[i-1][j-1] + 1;
if(a[i][j] > max) max = a[i][j];
}
}
}
return max;
}
int main()
{
printf("%d\n", f("abcdkkk", "baabcdadabc"));
printf("%d\n", f("aaakkkabababa", "baabababcdadabc"));
printf("%d\n", f("abccbaacbcca", "ccccbbbbbaaaa"));
printf("%d\n", f("abcd", "xyz"));
printf("%d\n", f("ab", "ab"));
return 0;
}