本文使用 AI 辅助整理生成,相关信息来源网络。
题目
一、单项选择题(共 15 题,每题 2 分,共计 30 分;每题有且仅有一个正确选项)
-
下列 C++ 数据类型中,能够精确存储 10 18 + 1 10^{18}+1 1018+1 这个整数的是( )
A. float B. long long C. double D. int
-
十六进制数 2 F 5 2F5 2F5 转换为八进制数是( )
A. 1364 B. 1635 C. 1405 D. 1365
-
执行下列 C++ 代码,输出是( )
cppint a = 7, b = 3; std::cout << a / b * b + a % b;A. 9 B. 10 C. 7 D. 6
-
初始时栈为空,将 1、2、3、4 依次入栈,入栈过程中允许随时出栈。下列出栈序列中不可能出现的是( )
A. 2,4,3,1 B. 1,2,3,4
C. 3,1,2,4 D. 1,4,3,2
-
一棵有 100 个结点的完全二叉树,其中叶子结点个数是( )
A. 49 B. 50 C. 64 D. 51
-
执行下列代码后 s 的值是( )
cppint s = 0; for (int i = 1; i <= 100; i++) if (i % 3 == 0 || i % 5 == 0) s += i;A. 3048 B. 2733 C. 2318 D. 2418
-
上楼梯每步可上 1 级、2 级或 3 级,从地面(可视为第 0 级)走到第 8 级台阶共有多少种不同走法( )
A. 44 B. 121 C. 149 D. 81
-
下图为 5 × 5 5 \times 5 5×5 网格,行号、列号均从 0 开始,# 为障碍,. 为可通行格:
S . . # . . . . # . . . . # . # # . . E . . . # .从 S 出发做广度优先搜索(BFS):初始时把 S 入队;每次取出队首格子,按"上、下、左、右"(上=行号减 1,下=行号加 1,左=列号减 1,右=列号加 1)的顺序遍历它的四个相邻格子,越界、障碍或已访问的格子跳过,其余格子标记为已访问并入队。当 E 第一次入队时,已经入队过的格子(含 S 和 E)共有多少个( )
A. 15 B. 12 C. 14 D. 13
-
满足 1 ≤ n ≤ 100 1 \le n \le 100 1≤n≤100 且 gcd ( n , 60 ) = 6 \gcd(n, 60) = 6 gcd(n,60)=6 的正整数 n n n 共有多少个( )
A. 8 B. 6 C. 4 D. 5
-
某国硬币面值为 1 元、4 元、6 元且数量不限,凑出 9 元最少需要多少枚( )
A. 3 B. 4 C. 5 D. 2
-
执行下列代码,输出是( )
cppint a[5] = {1, 3, 5, 7, 9}; int *p = a + 2; *(p - 1) = p[0] + p[2]; p[1] = *(a + 1) - a[0]; cout << a[1] << "," << a[3];A. 14,13 B. 8,13 C. 14,7 D. 14,2
-
在含 1000 个互不相同元素的升序数组中,用二分法查找给定值(返回元素位置或报告不存在),最坏情况下需要与数组元素比较多少次?( )
A. 500 B. 9 C. 11 D. 10
-
数组 a 1.. n a1..n a1..n 的前缀和数组 s s s(即 s i = a 1 + a 2 + ⋯ + a i si = a1 + a2 + \cdots + ai si=a1+a2+⋯+ai)满足 s i = 3 i 2 + i si = 3i^2 + i si=3i2+i。则 a 10 a10 a10 的值是( )
A. 252 B. 310 C. 58 D. 61
-
数轴上有 7 个点,坐标分别为 1、3、4、7、10、15、20。在数轴上选取一个整数坐标点 P P P,使 P P P 到这 7 个点的距离之和最小,这个最小距离和是( )
A. 37 B. 42 C. 40 D. 38
-
一个无向图有 10 个顶点,其中 4 个顶点的度为 3,其余顶点的度均为 4,则该图的边数是( )
A. 36 B. 18 C. 17 D. 20
二、阅读程序(程序输入不超过数组或字符串定义的范围;判断题正确填 √,错误填 ×;除特殊说明外,判断题 1.5 分,选择题 3 分,共计 40 分)
(1)
cpp
01 #include <iostream>
02 using namespace std;
03 int main() {
04 int n;
05 cin >> n;
06 int x = 1, y = 1;
07 while (n > 0) {
08 if (n % 2 == 0) {
09 ++x;
10 } else {
11 ++x;
12 ++y;
13 }
14 n = n / 2;
15 }
16 cout << x << ' ' << y << endl;
17 return 0;
18 }
以下问题均假定输入的 n n n 为不超过 2 31 − 1 2^{31}-1 231−1 的非负整数。
判断题
-
(1 分)当输入为 3 时,程序输出为 3 3。( )
-
将第 11 行的
++x;删除后,程序输出的两个数一定相等。( ) -
假设输入为非负整数,则程序输出的第一个数一定不小于第二个数。( )
单选题
- 将第 7 行的
while (n > 0)改为while (n >= 0)后,程序可能出现的问题是( )。
A. 陷入死循环 B. 输出结果比原来大
C. 输出结果比原来小 D. 输出结果不受影响
- 当输入为 6 时,输出为( )。
A. 3 3 B. 4 2 C. 4 3 D. 5 2
- 若输入 n n n 依次取遍 0 , 1 , 2 , ... , 2 31 − 1 0, 1, 2, \ldots, 2^{31}-1 0,1,2,...,231−1 中的所有整数,则程序输出的第二个数恰好为 2 的次数为( )。
A. 16 B. 30 C. 31 D. 32
(2)
cpp
01 #include <algorithm>
02 #include <iostream>
03 #include <string>
04 using namespace std;
05 int a[100007], b[100007], c[100007], carry[100007];
06 string input_str;
07 int a_len, b_len;
08 int main() {
09 cin >> input_str;
10 a_len = input_str.size();
11 for (int i = 0; i < a_len; i++) {
12 a[i] = input_str[a_len - i - 1] - '0';
13 }
14 cin >> input_str;
15 b_len = input_str.size();
16 for (int i = 0; i < b_len; i++) {
17 b[i] = input_str[b_len - i - 1] - '0';
18 }
19 carry[0] = 0;
20 for (int i = 0; i < max(a_len, b_len) + 1; i++) {
21 c[i] = a[i] + b[i] + carry[i];
22 if (c[i] >= 10) {
23 carry[i + 1] = 1;
24 c[i] -= 10;
25 } else {
26 carry[i + 1] = 0;
27 }
28 }
29 for (int i = max(a_len, b_len); i >= 0; i--) {
30 cout << c[i];
31 }
32 cout << endl;
33 return 0;
34 }
本题输入的两个数均为非负整数,位数不超过 100000,可能包含前导零。
判断题
-
当输入为
123 456时,程序输出为0579。( ) -
假设输入的两个数均不含前导零,则程序输出的结果也一定不会含有前导零。( )
-
将第 21 行改为
c[i]=a[i]+b[i];后,程序输出的结果一定比原来的结果小。( )
单选题
- 当输入为
12345 678时,输出为( )。
A. 012923 B. 013023 C. 13023 D. 130230
- 将第 22 行的
if (c[i]>=10)改为if (c[i]>10)后,当输入为95 15时,输出为( )。
A. 01010 B. 110 C. 140 D. 1410
- 假设输入的两个数均为 n n n 位正整数(不含前导零),且它们的和小于 10 n 10^n 10n,则程序输出的字符串一定满足( )。
A. 第一个字符一定不为 '0'
B. 长度一定为 n n n
C. 长度一定为 n + 1 n+1 n+1,且第一个字符为 '0'
D. 长度可能为 n + 2 n+2 n+2
(3)
cpp
01 #include <iostream>
02 using namespace std;
03 bool check_prime(int x) {
04 if (x <= 1) return false;
05 for (int i = 2; i * i <= x; i++) {
06 if (x % i == 0) return false;
07 }
08 return true;
09 }
10 int n;
11 void search_result(int x) {
12 if (!check_prime(x)) return;
13 if (x >= n) {
14 cout << x << endl;
15 return;
16 }
17 for (int i = 0; i <= 9; i++) {
18 search_result(x * 10 + i);
19 }
20 }
21 int main() {
22 cin >> n;
23 for (int i = 1; i <= 9; i++) search_result(i);
24 return 0;
25 }
判断题
-
当输入为 10 时,程序的输出共有 10 行。( )
-
若输入的 n n n 不大于 5,则程序的输出中一定包含 5。( )
-
若输入的 n n n 大于 10,将第 17 行的
for (int i=0;i<=9;i++)改为for (int i=1;i<=9;i+=2)后,程序的输出结果一定不变。( )
单选题
- 当输入为 24 时,程序输出的第 3 行为( )。
A. 23 B. 29 C. 31 D. 239
- 下列关于该程序输出的说法中,正确的是( )。
A. 输出的数一定按照从小到大的顺序排列
B. 随着输入 n n n 的增大,输出的行数一定不会增加
C. 输出的数的个位数字只可能是 3 或 7
D. 输出的每个大于等于 10 的数,十进制下删去它的末位数字后得到的数一定是质数
- 当输入为 200 时,程序输出的行数为( )。
A. 12 B. 13 C. 14 D. 15
三、完善程序(单选题,每小题 3 分,共计 30 分)
(1)(进制减半)给定 n , m n, m n,m,再给定一个 m n m^n mn 进制下的数 A A A,其各个数位上的数按照从高位到低位的顺序给出,请你将其转化为 n n n 进制,并同样按照从高位到低位的顺序输出。
输入的第一行依次为 n n n、 m m m 和 A A A 的位数 d d d,接下来 d d d 个数 a d , a d − 1 , ⋯ , a 1 a_d, a_{d-1}, \cdots, a_1 ad,ad−1,⋯,a1 从高位到低位描述各个数位上的数。
数据满足 2 ≤ n , m ≤ 10 2 \le n, m \le 10 2≤n,m≤10, 1 ≤ d ≤ 18 1 \le d \le 18 1≤d≤18, 0 ≤ A < 2 63 0 \le A < 2^{63} 0≤A<263,对于所有 1 ≤ i ≤ d 1 \le i \le d 1≤i≤d, 0 ≤ a i < m n 0 \le a_i < m^n 0≤ai<mn。
以下程序按"逐位除以 n n n"的方法完成进制转换。请补全程序。
cpp
01 #include <iostream>
02
03 constexpr int N = 100005;
04 long long b[N];
05
06 int main() {
07 long long n, m, d;
08 std::cin >> n >> m >> d;
09 int len = 1;
10 for (int i = 0; i < d; i++) {
11 long long x;
12 std::cin >> x;
13 for (int j = len; j >= 1; j--)
14 b[j] = ① ;
15 b[0] = ② ;
16 len++;
17 for (int j = 0; j < len; j++)
18 if (b[j] >= n) {
19 b[j + 1] += ③ ;
20 b[j] = ④ ;
21 if (j + 1 == len) len++;
22 }
23 }
24 while ( ⑤ ) len--;
25 for (int i = len - 1; i >= 0; i--)
26 std::cout << b[i] << ' ';
27 return 0;
28 }
- ①处应填( )
A.b[j] * nB.b[j] * m
C.b[j - 1] * nD.b[j - 1] * m - ②处应填( )
A.x * nB.xC.0D.m - ③处应填( )
A.b[j] / mB.b[j] % nC.b[j] % mD.b[j] / n - ④处应填( )
A.b[j] / mB.b[j] % nC.b[j] % mD.b[j] / n - ⑤处应填( )
A.len > 0 && b[len - 1] == 0
B.len > 0 && b[0] == 0
C.len > 1 && b[len - 1] == 0
D.len > 1 && b[0] == 0
(2)(平衡分割)给定一个长度为 n n n 的字符串,其中每个字符都是一个十六进制数位。例如,字符串 016A 表示十进制下的四个数 0、1、6、10。
现在请选择 k k k 个( k k k 是你选定的数)切分位置 p 1 , p 2 , ... , p k p_1, p_2, \ldots, p_k p1,p2,...,pk,其中 1 ≤ k < n 1 \le k < n 1≤k<n,且 1 ≤ p 1 < p 2 < ⋯ < p k < n 1 \le p_1 < p_2 < \cdots < p_k < n 1≤p1<p2<⋯<pk<n。再令 p 0 = 0 p_0 = 0 p0=0, p k + 1 = n p_{k+1} = n pk+1=n。
对于每个 0 ≤ i ≤ k 0 \le i \le k 0≤i≤k,计算第 p i + 1 p_i + 1 pi+1 个数到第 p i + 1 p_{i+1} pi+1 个数的平均值,记作 b i b_i bi。你的目标是使 b 0 , b 1 , ... , b k b_0, b_1, \ldots, b_k b0,b1,...,bk 中最大值与最小值之差尽可能小,并输出这个最小值。
其中 2 ≤ n ≤ 20 2 \le n \le 20 2≤n≤20。输入字符串中的字符只可能是 0~9 或 A~F。本题假定字符采用 ASCII 编码。输出答案时保留小数点后 6 位。
以下程序通过递归枚举所有可能的连续分段方案。请补全程序。
cpp
01 #include <algorithm>
02 #include <iomanip>
03 #include <iostream>
04
05 using namespace std;
06
07 constexpr int N = 25;
08
09 int n, a[N];
10 char s[N];
11
12 double ans = 1e100;
13
14 int value(char c) { return ① ; }
15
16 void split(int l, int cnt, double mnb, double mxb) {
17 if (l > n) {
18 if (cnt == 0) return;
19 ans = min(ans, mxb - mnb);
20 return;
21 }
22 int sum = 0;
23 for ( ② ) {
24 sum += a[r];
25 double nwb = ③ ;
26 split( ④ );
27 }
28 }
29
30 int main() {
31 cin >> n >> s + 1;
32 for (int i = 1; i <= n; ++i)
33 a[i] = value(s[i]);
34 split( ⑤ );
35 cout << fixed << setprecision(6) << ans;
36 return 0;
37 }
- ①处应填( )
A.c - (c < '9' ? '0' : 'A' - 10)
B.c - (c < 'A' ? '0' : 'A' - 10)
C.c - (c < 'A' ? 'A' - 10 : '0')
D.c - (c < 'A' ? '0' : 'A' + 10) - ②处应填( )
A.int r = l + 1; r <= n; ++r
B.int r = l; r < n; ++r
C.int r = l; r <= n; r += 2
D.int r = l; r <= n; ++r - ③处应填( )
A.sum / (r - l + 1) * 1.0
B.sum * 1.0 / (r - l) + 1
C.sum * 1.0 / (r - l + 1)
D.(sum - a[r]) * 1.0 / (r - l + 1) - ④处应填( )
A.r + 1, cnt + (r < n), min(mnb, nwb), max(mxb, nwb)
B.r + 1, cnt + (r <= n), min(mnb, nwb), max(mxb, nwb)
C.r + 1, cnt + (r < n), max(mnb, nwb), min(mxb, nwb)
D.r + 1, cnt + (r <= n), max(mnb, nwb), min(mxb, nwb) - ⑤处应填( )
A.0, 0, 1e100, -1e100B.0, 0, -1e100, 1e100
C.1, 0, -1e100, 1e100D.1, 0, 1e100, -1e100
答案及解析(GPT给出,不保证正确)
答案部分参考洛谷,解析由GPT给出。
答案速查
| 题号 | 答案 | 题号 | 答案 | 题号 | 答案 |
|---|---|---|---|---|---|
| 1 | B | 6 | D | 11 | A |
| 2 | D | 7 | D | 12 | D |
| 3 | C | 8 | C | 13 | C |
| 4 | C | 9 | B | 14 | A |
| 5 | B | 10 | A | 15 | B |
| 16 | √ | 22 | √ | 28 | × |
| 17 | × | 23 | × | 29 | √ |
| 18 | √ | 24 | × | 30 | √ |
| 19 | A | 25 | B | 31 | B |
| 20 | C | 26 | A | 32 | D |
| 21 | C | 27 | C | 33 | C |
| 题号 | 答案 | 填入内容 |
|---|---|---|
| 34 | D | b[j - 1] * m |
| 35 | B | x |
| 36 | D | b[j] / n |
| 37 | B | b[j] % n |
| 38 | C | len > 1 && b[len - 1] == 0 |
| 39 | B | c - (c < 'A' ? '0' : 'A' - 10) |
| 40 | D | int r = l; r <= n; ++r |
| 41 | C | sum * 1.0 / (r - l + 1) |
| 42 | A | r + 1, cnt + (r < n), min(mnb, nwb), max(mxb, nwb) |
| 43 | D | 1, 0, 1e100, -1e100 |
一、单项选择题
第 1 题(答案 B)
10 18 + 1 10^{18}+1 1018+1 是整数,需要整型类型精确表示。long long 通常占 64 位,范围约为 − 9.22 × 10 18 , 9.22 × 10 18 -9.22\\times10\^{18},\\;9.22\\times10\^{18} −9.22×1018,9.22×1018, 10 18 + 1 10^{18}+1 1018+1 能精确存放;int 放不下;float/double 是浮点,尾数只有 23/53 位,无法精确表示 10 18 + 1 10^{18}+1 1018+1。
第 2 题(答案 D)
2 F 5 16 = 2 × 16 2 + 15 × 16 + 5 = 757 2F5_{16}=2\times16^2+15\times16+5=757 2F516=2×162+15×16+5=757。
把 757 757 757 转八进制:
757 ÷ 8 = 94 ⋯ 5 , 94 ÷ 8 = 11 ⋯ 6 , 11 ÷ 8 = 1 ⋯ 3 , 1 ÷ 8 = 0 ⋯ 1 757\div8=94\cdots5,\;94\div8=11\cdots6,\;11\div8=1\cdots3,\;1\div8=0\cdots1 757÷8=94⋯5,94÷8=11⋯6,11÷8=1⋯3,1÷8=0⋯1
从下往上读得 1365 8 1365_8 13658。
第 3 题(答案 C)
整数除法 a / b = 7 / 3 = 2 a/b=7/3=2 a/b=7/3=2, a % b = 1 a\%b=1 a%b=1,所以
a / b ∗ b + a % b = 2 × 3 + 1 = 7 a/b*b+a\%b=2\times3+1=7 a/b∗b+a%b=2×3+1=7
第 4 题(答案 C)
序列 3,1,2,4 不可能。要让 3 先出,必须先把 1,2,3 都入栈;此时栈顶是 3,下面是 2,再下面是 1。3 出栈后,下一步不可能直接弹出 1,因为 2 还在 1 上面。
第 5 题(答案 B)
完全二叉树中,度为 1 1 1 的结点最多 1 1 1 个,其余非叶结点都有两个孩子。 100 100 100 个结点中,内部结点数为 ⌊ 100 / 2 ⌋ = 50 \lfloor100/2\rfloor=50 ⌊100/2⌋=50,所以叶子数为 100 − 50 = 50 100-50=50 100−50=50。
第 6 题(答案 D)
求 1 ∼ 100 1\sim100 1∼100 中能被 3 3 3 或 5 5 5 整除的数之和:
S 3 = 3 + 6 + ⋯ + 99 = 3 ( 1 + 2 + ⋯ + 33 ) = 3 × 33 × 34 2 = 1683 S 5 = 5 + 10 + ⋯ + 100 = 5 ( 1 + 2 + ⋯ + 20 ) = 5 × 20 × 21 2 = 1050 S 15 = 15 + 30 + ⋯ + 90 = 15 × 6 × 7 2 = 315 S = S 3 + S 5 − S 15 = 2418 \begin{aligned} S_3&=3+6+\cdots+99=3(1+2+\cdots+33)=3\times\frac{33\times34}{2}=1683\\ S_5&=5+10+\cdots+100=5(1+2+\cdots+20)=5\times\frac{20\times21}{2}=1050\\ S_{15}&=15+30+\cdots+90=15\times\frac{6\times7}{2}=315\\ S&=S_3+S_5-S_{15}=2418 \end{aligned} S3S5S15S=3+6+⋯+99=3(1+2+⋯+33)=3×233×34=1683=5+10+⋯+100=5(1+2+⋯+20)=5×220×21=1050=15+30+⋯+90=15×26×7=315=S3+S5−S15=2418
第 7 题(答案 D)
设 f ( i ) f(i) f(i) 为走到第 i i i 级的方法数,递推
f ( i ) = f ( i − 1 ) + f ( i − 2 ) + f ( i − 3 ) f(i)=f(i-1)+f(i-2)+f(i-3) f(i)=f(i−1)+f(i−2)+f(i−3)
边界 f ( 0 ) = 1 , f ( 1 ) = 1 , f ( 2 ) = 2 f(0)=1,\;f(1)=1,\;f(2)=2 f(0)=1,f(1)=1,f(2)=2。递推得:
f ( 3 ) = 4 , f ( 4 ) = 7 , f ( 5 ) = 13 , f ( 6 ) = 24 , f ( 7 ) = 44 , f ( 8 ) = 81 f(3)=4,\;f(4)=7,\;f(5)=13,\;f(6)=24,\;f(7)=44,\;f(8)=81 f(3)=4,f(4)=7,f(5)=13,f(6)=24,f(7)=44,f(8)=81
第 8 题(答案 C)
按题意 BFS,方向顺序为"上、下、左、右"。模拟入队过程,当 E E E 第一次入队时,已入队格子(含 S S S、 E E E)共 14 14 14 个。
关键路径示例:
S ( 0 , 0 ) → ( 1 , 0 ) → ( 0 , 1 ) → ( 2 , 0 ) → ( 0 , 2 ) → ( 2 , 1 ) → ( 1 , 2 ) → ( 2 , 2 ) → ( 3 , 2 ) → ( 4 , 2 ) → ( 3 , 3 ) → E ( 3 , 4 ) S(0,0)\to(1,0)\to(0,1)\to(2,0)\to(0,2)\to(2,1)\to(1,2)\to(2,2)\to(3,2)\to(4,2)\to(3,3)\to E(3,4) S(0,0)→(1,0)→(0,1)→(2,0)→(0,2)→(2,1)→(1,2)→(2,2)→(3,2)→(4,2)→(3,3)→E(3,4)。
第 9 题(答案 B)
60 = 2 2 × 3 × 5 60=2^2\times3\times5 60=22×3×5, gcd ( n , 60 ) = 6 = 2 × 3 \gcd(n,60)=6=2\times3 gcd(n,60)=6=2×3 说明 n n n 必须恰好含一个因子 2 2 2、一个因子 3 3 3,且不含因子 5 5 5。
设 n = 6 k n=6k n=6k,则 gcd ( k , 10 ) = 1 \gcd(k,10)=1 gcd(k,10)=1,且 1 ≤ 6 k ≤ 100 ⇒ 1 ≤ k ≤ 16 1\le 6k\le100\Rightarrow 1\le k\le16 1≤6k≤100⇒1≤k≤16。
与 10 10 10 互质的 k k k 有: 1 , 3 , 7 , 9 , 11 , 13 1,3,7,9,11,13 1,3,7,9,11,13,共 6 6 6 个。
第 10 题(答案 A)
凑 9 9 9 元。尽量用面值大的硬币:
- 6 + 1 + 1 + 1 = 4 6+1+1+1=4 6+1+1+1=4 枚
- 4 + 4 + 1 = 3 4+4+1=3 4+4+1=3 枚
最少 3 3 3 枚。
第 11 题(答案 A)
初始数组 a = {1,3,5,7,9},p = a + 2 指向 a[2]=5。
*(p-1) = p[0] + p[2]:修改a[1] = 5 + 9 = 14。p[1] = *(a+1) - a[0]:此时a[1]已经是 14 14 14,所以a[3] = 14 - 1 = 13。
输出 a[1],a[3] 为 14,13。
第 12 题(答案 D)
二分查找最坏比较次数为
⌈ log 2 ( 1000 ) ⌉ \lceil\log_2(1000)\rceil ⌈log2(1000)⌉
因为 2 9 = 512 < 1000 ≤ 1024 = 2 10 2^9=512<1000\le1024=2^{10} 29=512<1000≤1024=210,所以最坏需要 10 10 10 次比较。
第 13 题(答案 C)
前缀和定义 s i = a 1 + a 2 + ⋯ + a i si=a_1+a_2+\cdots+a_i si=a1+a2+⋯+ai,所以 a i = s i − s i − 1 a_i=si-si-1 ai=si−si−1。
a 10 = s 10 − s 9 = ( 3 × 10 2 + 10 ) − ( 3 × 9 2 + 9 ) = 310 − 252 = 58 a_{10}=s_{10}-s_9=(3\times10^2+10)-(3\times9^2+9)=310-252=58 a10=s10−s9=(3×102+10)−(3×92+9)=310−252=58
第 14 题(答案 A)
数轴上一点到若干点的距离之和最小,取这些点的中位数 。 7 7 7 个数的中位数是第 4 4 4 个,即 7 7 7。
最小距离和为
∣ 1 − 7 ∣ + ∣ 3 − 7 ∣ + ∣ 4 − 7 ∣ + ∣ 7 − 7 ∣ + ∣ 10 − 7 ∣ + ∣ 15 − 7 ∣ + ∣ 20 − 7 ∣ = 6 + 4 + 3 + 0 + 3 + 8 + 13 = 37 |1-7|+|3-7|+|4-7|+|7-7|+|10-7|+|15-7|+|20-7|=6+4+3+0+3+8+13=37 ∣1−7∣+∣3−7∣+∣4−7∣+∣7−7∣+∣10−7∣+∣15−7∣+∣20−7∣=6+4+3+0+3+8+13=37
第 15 题(答案 B)
无向图中所有顶点度数之和等于边数的 2 2 2 倍。
度数和 = 4 × 3 + 6 × 4 = 12 + 24 = 36 =4\times3+6\times4=12+24=36 =4×3+6×4=12+24=36,所以边数 = 36 / 2 = 18 =36/2=18 =36/2=18。
二、阅读程序
程序(1)
程序把 n n n 的二进制从低位到高位逐位处理:
- 每处理一位,
x必然加 1 1 1; - 若该位为 1 1 1,
y也加 1 1 1。
因此输出 x = x= x=(二进制位数) + 1 +1 +1, y = y= y=( n n n 的二进制中 1 1 1 的个数) + 1 +1 +1。
16. √
n = 3 = ( 11 ) 2 n=3=(11)_2 n=3=(11)2,两位都是 1 1 1,循环两次,x 加 2 2 2 变 3 3 3,y 加 2 2 2 变 3 3 3。输出 3 3。
17. ×
删除 else 分支里的 ++x; 后,奇数位只加 y 不加 x。例如 n = 1 n=1 n=1:
- 原来: x = 2 , y = 2 x=2,\;y=2 x=2,y=2;
- 删除后: x = 1 , y = 2 x=1,\;y=2 x=1,y=2。
不一定相等。
18. √
每次循环 x 至少加 1 1 1,y 至多加 1 1 1,所以始终有 x ≥ y x\ge y x≥y。
19. A
改成 while (n >= 0) 后,当 n n n 减小到 0 0 0 时条件仍成立,执行 n = n / 2 n=n/2 n=n/2 后 n n n 仍为 0 0 0,陷入死循环。
20. C
n = 6 = ( 110 ) 2 n=6=(110)_2 n=6=(110)2,共 3 3 3 位,其中 1 1 1 的个数为 2 2 2。所以 x = 1 + 3 = 4 x=1+3=4 x=1+3=4, y = 1 + 2 = 3 y=1+2=3 y=1+2=3,输出 4 3。
21. C
输出的第二个数 y = 2 y=2 y=2 等价于 n n n 的二进制中恰好有 1 1 1 个 1 1 1。在 0 , 2 31 − 1 0,2\^{31}-1 0,231−1 中,形如 2 k 2^k 2k 的数有
k = 0 , 1 , 2 , ... , 30 k=0,1,2,\ldots,30 k=0,1,2,...,30
共 31 31 31 个。
程序(2)
程序读入两个非负整数(允许前导零),按低位到高位存入数组 a、b,再做带进位加法,最后从高位到低位输出结果(会保留最高位的进位 0 0 0)。
22. √
123 + 456 = 579。由于结果只产生 3 3 3 位,程序会额外输出最高位的进位 c 3 = 0 c3=0 c3=0,所以输出 0579。
23. ×
即使输入没有前导零,和也可能没有产生新的最高位进位,导致程序输出一个前导 0 0 0。例如第 22 22 22 题就是反例。
24. ×
去掉进位后,每位可能直接输出 10 ∼ 18 10\sim18 10∼18 的数字,结果反而变大,而不是一定变小。
25. B
12345 + 678 = 13023。程序会输出 4 4 4 位结果加一个前导进位 0 0 0,即 013023。
26. A
把 >=10 改成 >10 后, c i = 10 ci=10 ci=10 时不会进位,直接输出 10。
对输入 95 15:
- 个位: 5 + 5 = 10 5+5=10 5+5=10,输出
10; - 十位: 9 + 1 = 10 9+1=10 9+1=10,输出
10; - 最高位进位 0 0 0。
拼接起来就是 01010。
27. C
两个 n n n 位正整数相加,和小于 10 n 10^n 10n,说明结果最多 n n n 位,不会产生新的最高位进位。程序固定输出 max(a_len,b_len)+1 = n+1 位,且最高位是进位 0 0 0,因此长度一定为 n + 1 n+1 n+1 且首字符为 '0'。
程序(3)
函数 search_result(x) 按 DFS 扩展数字 x x x:
- 若 x x x 不是质数,直接返回;
- 若 x ≥ n x\ge n x≥n,输出并返回(不再往下扩展);
- 否则在 x x x 后接 0 ∼ 9 0\sim9 0∼9 继续递归。
输出的数具有性质:它的每一位前缀都是质数。
28. ×
经DEV测试,只有9行。
29. √
若 n ≤ 5 n\le5 n≤5,单数位质数 5 ≥ n 5\ge n 5≥n 一定被输出(种子 5 5 5 本身会被调用)。
30. √
当 n > 10 n>10 n>10 时,输出的都是至少两位的质数。一个大于 10 10 10 的质数末位只能是 1 , 3 , 7 , 9 1,3,7,9 1,3,7,9,所以删去偶数位和 5 5 5 后,所有可能的扩展仍然保留。
31. B
n = 24 n=24 n=24 时,DFS 输出的前几行为:
233(前缀 23 23 23 是质数,继续扩展到 233 233 233)23929
第 3 3 3 行为 29 29 29。
32. D
- A:错误。例如 n = 24 n=24 n=24 时,先输出
233、239,再输出29,不是递增。 - B:错误。 n n n 增大时,某些"浅层"质数会变小于 n n n,程序会继续向下搜索,可能输出更多 deeper 质数。
- C:错误。例如
233的个位是 3 3 3,但239的个位是 9 9 9。 - D:正确。输出的每个多位数 x x x 都是在它的所有前缀都是质数的前提下才生成的,去掉末位得到的前缀一定是质数。
33. C
n = 200 n=200 n=200 时,逐一枚举 DFS 边界质数:
- 从 2 2 2 出发: 233 , 239 , 29 233,239,29 233,239,29( 3 3 3 个)
- 从 3 3 3 出发: 31 , 311 , 313 , 317 , 37 , 373 , 379 31,311,313,317,37,373,379 31,311,313,317,37,373,379( 7 7 7 个)
- 从 5 5 5 出发: 59 59 59( 1 1 1 个)
- 从 7 7 7 出发: 719 , 733 , 739 , 79 719,733,739,79 719,733,739,79( 4 4 4 个)
合计 3 + 7 + 1 + 4 = 14 3+7+1+4=14 3+7+1+4=14 行。
三、完善程序
(1)进制减半
题目要求把 m n m^n mn 进制数转换为 n n n 进制。数组 b 从低位到高位保存 n n n 进制结果。
34. D:b[j - 1] * m
新读入一个 m n m^n mn 进制位,相当于把整个当前 n n n 进制数乘以 m n m^n mn。因为 m n m^n mn 在 n n n 进制下表示为"在第 1 1 1 位放 m m m",所以原第 j − 1 j-1 j−1 位要移到第 j j j 位并乘以 m m m。
35. B:x
新读入的位 x x x 作为当前 n n n 进制数的最低位,放到 b[0]。
36. D:b[j] / n
当 b j ≥ n bj\ge n bj≥n 时,向高位进位,进位值就是 b j bj bj 除以 n n n 的商。
37. B:b[j] % n
当前位保留除以 n n n 的余数。
38. C:len > 1 && b[len - 1] == 0
输出前去掉高位的连续 0 0 0,但要保证至少保留一位(len > 1)。
(2)平衡分割
把十六进制字符串切成若干连续段,使各段平均值的最大值与最小值之差最小。
39. B:c - (c < 'A' ? '0' : 'A' - 10)
把十六进制字符转成数值:
'0'\sim'9':减去'0';'A'\sim'F':减去'A'-10。
40. D:int r = l; r <= n; ++r
枚举当前段的结束位置 r r r,从当前起点 l l l 开始,到字符串末尾 n n n 结束。
41. C:sum * 1.0 / (r - l + 1)
段 l , r l,r l,r 的平均值为和除以元素个数,个数为 r − l + 1 r-l+1 r−l+1。
42. A:r + 1, cnt + (r < n), min(mnb, nwb), max(mxb, nwb)
- 下一段从 r + 1 r+1 r+1 开始;
cnt记录已做的切分次数,只有当 r < n r<n r<n 时才产生一次新切分;- 用当前段平均值
nwb更新全局最小/最大值。
43. D:1, 0, 1e100, -1e100
初始调用从位置 1 1 1 开始,尚未切分(cnt=0),当前最小值初始为正无穷,最大值初始为负无穷,方便后续取 min / max \min/\max min/max。