🍭 大家好这里是清隆学长 ,一枚热爱算法的程序员
✨ 本系列打算持续跟新b站近期的春秋招笔试题汇总~
💻 ACM银牌🥈| 多次AK大厂笔试 | 编程一对一辅导
👏 感谢大家的订阅➕ 和 喜欢💗
📧 清隆这边最近正在收集近一年互联网各厂的笔试题汇总,如果有需要的小伙伴可以关注后私信一下 清隆领取,会在飞书进行同步的跟新。
文章目录
- 🎀 01.K小姐的生日派对
- 题目描述
- 输入格式
- 输出格式
- 样例输入
- 样例输出
- 数据范围
- 题解
- 参考代码
- 🍓 02.K小姐的字符串翻转
- 问题描述
- 输入格式
- 输出格式
- 样例输入
- 样例输出
- 数据范围
- 题解
- 参考代码
- 写在最后
- 📧 清隆这边最近正在收集近一年互联网各厂的笔试题汇总,如果有需要的小伙伴可以关注后私信一下 清隆领取,会在飞书进行同步的跟新。
🎀 01.K小姐的生日派对
题目描述
K小姐即将迎来自己的生日,为了庆祝这个特殊的日子,她邀请了 n n n 位朋友参加生日派对。朋友们围坐在一张大圆桌周围,我们按照顺时针的方向将他们编号为 1 , 2 , … , n 1,2,\ldots,n 1,2,…,n。
现在,K小姐想在朋友中选出一些人组成一个小组,并为这个小组拍照留念。为了照片的和谐美观,小组中的所有人必须坐在一起。K小姐想知道,一共有多少种不同的选择方案呢?
注意:
- 由于圆桌的特殊性,编号为 1 1 1 的朋友同时与编号为 2 2 2 和 n n n 的朋友相邻。
- 两个方案不同,当且仅当选出的朋友个数不同或者选出的朋友编号不完全相同。
输入格式
输入一个正整数 n n n,表示朋友的人数。
输出格式
输出一个整数,表示总的方案数。
样例输入
4
样例输出
13
数据范围
- 对于 10 % 10\% 10% 的数据, 1 ≤ n ≤ 5 1 \leq n \leq 5 1≤n≤5。
- 对于 30 % 30\% 30% 的数据, 1 ≤ n ≤ 100 1 \leq n \leq 100 1≤n≤100。
- 对于 60 % 60\% 60% 的数据, 1 ≤ n ≤ 1000 1 \leq n \leq 1000 1≤n≤1000。
- 对于 100 % 100\% 100% 的数据, 1 ≤ n ≤ 1 0 9 1 \leq n \leq 10^9 1≤n≤109。
题解
本题可以通过数学分析的方法求解。我们将所有可能的方案分为两类:
-
普通方案:即选出的朋友不是圆桌上所有人。在这种情况下,我们可以从任意一位朋友开始选择,然后再选出其之后(顺时针方向)连续的 0 0 0 到 n − 2 n-2 n−2 位朋友,共 n ( n − 1 ) n(n-1) n(n−1) 种方案。
-
特殊方案:选出圆桌上所有的朋友。这种情况只有 1 1 1 种方案。
因此,总的方案数为 n ( n − 1 ) + 1 n(n-1)+1 n(n−1)+1。
时间复杂度 O ( 1 ) O(1) O(1),空间复杂度 O ( 1 ) O(1) O(1)。
参考代码
- Python
n = int(input())
print(n * (n - 1) + 1)
- Java
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
int n = sc.nextInt();
System.out.println(n * (n - 1) + 1);
}
}
- Cpp
#include <iostream>
using namespace std;
int main() {
int n;
cin >> n;
cout << n * (n - 1) + 1 << endl;
return 0;
}
🍓 02.K小姐的字符串翻转
问题描述
K小姐有一个长度为 n n n 的字符串 s s s,她想对这个字符串进行一些操作。具体来说,她会选择一个正整数 k k k,然后进行 n − k + 1 n-k+1 n−k+1 次操作,第 i i i 次操作会将字符串中从第 i i i 个字符到第 i + k − 1 i+k-1 i+k−1 个字符这一段翻转。
例如,当 n = 5 n=5 n=5, k = 3 k=3 k=3, s = “hello" s=\text{``hello"} s=“hello" 时:
- 第 1 次操作将 s [ 1 , 3 ] s[1,3] s[1,3] 翻转,得到 “lehlo" \text{``lehlo"} “lehlo";
- 第 2 次操作将 s [ 2 , 4 ] s[2,4] s[2,4] 翻转,得到 “llheo" \text{``llheo"} “llheo";
- 第 3 次操作将 s [ 3 , 5 ] s[3,5] s[3,5] 翻转,得到 “lloeh" \text{``lloeh"} “lloeh"。
因此最终得到的字符串 s s s 为 “lloeh" \text{``lloeh"} “lloeh"。
现在给定 n , k n,k n,k 和初始的字符串 s s s,请你求出经过这 n − k + 1 n-k+1 n−k+1 次操作后得到的字符串。
输入格式
第一行包含两个正整数 n n n 和 k k k。
第二行包含一个长度为 n n n 的仅由小写字母构成的字符串 s s s。
输出格式
输出一行,表示最终得到的字符串。
样例输入
5 3
hello
样例输出
lloeh
数据范围
- 2 ≤ k ≤ n ≤ 2 × 1 0 5 2 \leq k \leq n \leq 2\times 10^5 2≤k≤n≤2×105
题解
可以观察到,对于字符串的每个位置,它被翻转的次数取决于它的位置:
- 对于前 k − 1 k-1 k−1 个字符和后 k − 1 k-1 k−1 个字符,随着翻转区间的滑动,它们被翻转的次数变化趋势为 1 → k → 1 1 \to k \to 1 1→k→1。如果 n − k n-k n−k 是奇数,则这部分字符的翻转次数为奇数;如果 n − k n-k n−k 是偶数,则翻转次数为偶数。
- 对于中间的 n − 2 k + 2 n-2k+2 n−2k+2 个字符(如果有的话),它们都会被翻转 k k k 次,这是一个固定的偶数次。
因此,可以根据 n − k n-k n−k 的奇偶性,分别处理前 k − 1 k-1 k−1 个字符和后面的部分:
- 如果 n − k n-k n−k 是奇数,则前 k − 1 k-1 k−1 个字符需要翻转,后面的部分保持原样;
- 如果 n − k n-k n−k 是偶数,则前 k − 1 k-1 k−1 个字符保持原样,后面的部分需要翻转。
时间复杂度为 O ( n ) O(n) O(n),空间复杂度为 O ( n ) O(n) O(n)。
参考代码
- Python
n, k = map(int, input().split())
s = input()
if (n - k) % 2 != 0:
print(s[k - 1:] + s[:k - 1][::-1])
else:
print(s[k - 1:] + s[:k - 1])
- Java
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
int n = sc.nextInt();
int k = sc.nextInt();
String s = sc.next();
if ((n - k) % 2 != 0) {
System.out.println(s.substring(k - 1) + new StringBuilder(s.substring(0, k - 1)).reverse());
} else {
System.out.println(s.substring(k - 1) + s.substring(0, k - 1));
}
}
}
- Cpp
#include <iostream>
#include <algorithm>
#include <string>
using namespace std;
int main() {
int n, k;
string s;
cin >> n >> k >> s;
if ((n - k) % 2 != 0) {
reverse(s.begin(), s.begin() + k - 1);
}
cout << s.substr(k - 1) + s.substr(0, k - 1) << endl;
return 0;
}
写在最后
📧 清隆这边最近正在收集近一年互联网各厂的笔试题汇总,如果有需要的小伙伴可以关注后私信一下 清隆领取,会在飞书进行同步的跟新。