1 条题解

  • 0
    @ 2026-6-19 10:30:58

    📝 题目大意

    NN 张卡片从上到下堆叠,每张卡片上写有一个整数。从底部取出 KK 张卡片,保持原有顺序不变,整体放到顶部。输出操作后从上到下的卡片序列。

    💡 解题思路

    1. 题目分析N100N \leq 100,数据规模极小,直接模拟即可。关键约束是 1K<N1 \leq K < N,保证操作非平凡。
    2. 算法推导
      • 原序列从上到下为 A1,A2,,ANA_1, A_2, \dots, A_N
      • 底部 KK 张卡片为 ANK+1,ANK+2,,ANA_{N-K+1}, A_{N-K+2}, \dots, A_N
      • 将它们移到顶部后,新序列变为:ANK+1,,AN,A1,A2,,ANKA_{N-K+1}, \dots, A_N, A_1, A_2, \dots, A_{N-K}
      • 因此只需从下标 pos = N - K + 1 开始,循环遍历数组 NN 次,下标超出 NN 时回到 11
      • 代码中 k %= n 是防御性写法(虽然题目保证 K<NK < N),pos = n - k + 1 定位新起点,cnt 控制输出 NN 个数,pos++ 后若 pos > n 回绕到 1
    3. 边界与细节
      • K<NK < N 恒成立,不存在 K=NK = N 导致输出与原序列相同的情况(但即便出现,k %= n 会使 k = 0pos = n + 1,回绕后等价于 pos = 1,仍然正确)。
      • 输出末尾不能有多余空格,但本题评测通常容忍行末空格,且样例输出带空格,直接按代码格式输出即可。

    ⏱️ 复杂度分析

    • 时间复杂度O(N)O(N),遍历数组一次。
    • 空间复杂度O(N)O(N),存储数组 AA

    💻 标准代码 (C++)

    #include <bits/stdc++.h>
    using namespace std;
    
    int main () {
    	int n, k, a[105];
    	scanf("%d%d", &n, &k);
    	for (int i = 1; i <= n; i++) scanf("%d", &a[i]);  // 1-indexed 读取卡片序列
    	k %= n;                        // 防御性取模,避免 k >= n 的异常情况
    	int pos = n - k + 1, cnt = 1;  // pos: 新序列的起始下标(底部 K 张的第一张)
    	while (true) {
    		printf("%d ", a[pos]);     // 输出当前卡片
    		cnt++;
    		if (cnt > n) break;        // 已输出 N 个数,结束
    		pos++;
    		if (pos > n) pos = 1;      // 循环回绕
    	}
    	return 0;
    }
    
    • 1

    信息

    ID
    817
    时间
    1000ms
    内存
    256MiB
    难度
    10
    标签
    (无)
    递交数
    1
    已通过
    1
    上传者