Contestant. Rank 2570. Rating +70.
A. GamingForces
题意
给定一个数组
- 将其中两个元素减
- 将某个元素减为
输出最少的操作数,使
思路
将所有为
时间复杂度:最坏
对应AC代码
import java.util.*;
public class Main{
public static void main(String[] args){
Scanner scanner = new Scanner(System.in);
int t = scanner.nextInt();
while(t -- > 0){
int n = scanner.nextInt();
int cnt = 0;
for(int i=0;i<n;i++) if(scanner.nextInt() == 1) cnt ++;
System.out.println(n - cnt / 2);
}
}
}
简单签到题
B. Stand-up Comedian
题意
给定整数
和 都喜欢 喜欢, 不喜欢 喜欢, 不喜欢 和 都不喜欢
初始状态下,两人的心情值都为
输出最多能讲多少个笑话。
思路
模拟+思维
首先,我们先把类型
接着,我们讨论
否则,将
时间复杂度:
对应AC代码
import java.util.*;
public class Main{
public static void main(String[] args){
Scanner scanner = new Scanner(System.in);
int t = scanner.nextInt();
while(t -- > 0){
int[] a = new int[4];
for(int i=0;i<4;i++) a[i] = scanner.nextInt();
if(a[0] == 0){
System.out.println(1);
continue;
}
int n = Math.min(a[1], a[2]), ans = 0;
ans += a[0] + n * 2;
int m = Math.max(a[1] - n, a[2] - n);
if(a[0] < m){
System.out.println(2 * (a[0] + n) + 1);
}else{
ans += m;
ans += Math.min(a[0] - m + 1, a[3]);
System.out.println(ans);
}
}
}
}
思路好乱
C. Min Max Sort
题意
给定一个排列
思路
逆向思维
显然,我们需要对形如
考虑到一个不需要移动的元素对,应满足三个条件:
在 前面 在 前面 在 前面
筛出所有不需要移动的元素对并取补集即可。
时间复杂度:
对应AC代码
import java.util.*;
public class Main{
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int t = scanner.nextInt();
while (t-- > 0) {
int n = scanner.nextInt();
int[] w = new int[n + 1];
int ans = n / 2;
for (int i = 1; i <= n; i++) w[scanner.nextInt()] = i;
for (int i = n / 2; i >= 1; i--) { //排除不用移动的
if (w[i] < w[i + 1] && w[n - i + 1] > w[n - i] && w[i] < w[n - i + 1]) ans--;
else break;
}
System.out.println(ans);
}
}
}
反着想简单多了
D. Fixed Prefix Permutations
题意
给定整数
思路
显然,对于给定的排列
对于所有
为了让匹配的复杂度降到最低,我们可以采用字典树。
时间复杂度:
对应AC代码
#include <bits/stdc++.h>
using namespace std;
const int N = 50010;
int n, m;
int a[N][20], tmp[20];
class Trie {
private:
vector<Trie*> children;
public:
Trie() : children(12){}
void insert() {
Trie* node = this;
for (int i=0;i<m;i++) {
int ch = tmp[i];
if (node->children[ch] == nullptr) {
node->children[ch] = new Trie();
}
node = node->children[ch];
}
}
int find(int index) {
Trie* node = this;
int dep = 0;
for (int i=0;i<m;i++) {
int ch = a[index][i];
if (node->children[ch] == nullptr) {
return dep - 1;
}
node = node->children[ch];
dep ++;
}
return dep;
}
};
int main() {
ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
int t;
cin >> t;
while(t --){
Trie root = *new Trie();
cin >> n >> m;
for(int i=0;i<n;i++){
for(int j=1;j<=m;j++){
cin >> a[i][j];
tmp[a[i][j]] = j;
}
root.insert();
}
for(int i=0;i<n;i++){
cout << root.find(i) << " ";
}
cout << '\n';
}
}
题目真的很难看懂…
- 本文链接 https://floating-ocean.github.io/blog_old/posts/3006209530/
- 版权声明 本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!