手速思路还是太慢了,放假后要抓紧练习才行
A. XXXXX
主要思路: 首先求出全部的和是否是x的倍数,如果不是,则输出n, 如果是,那么找前后第一个余数不为0的点即可。
解题思路:
- 首先我们对所有数求和,如果不是x的倍数,那么直接输出n
- 然后我们判断是x的倍数的情况,那么我们只要前后找一个位置,这个位置他不是x的倍数即可,然后我们求这个长度的最大值。
代码:
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
typedef long long ll;
const int N = 100010, M = 200010;
int a[N];
int main(){
int T;
scanf("%d",&T);
while(T--){
int n, m;
scanf("%d%d",&n,&m);
for (int i = 1; i <= n; i++){
scanf("%d",&a[i]);
}
int res = 0;
int x = n + 1, y = 0;
for (int i = 1; i <= n; i++){
if (a[i] % m != 0){
if (x == n + 1) x = i;
if (y < i) y = i;
}
res += a[i];
}
if (res % m != 0) printf("%d\n",n);
else{
if (x != n + 1 && y != 0){
printf("%d\n",n - min(x,n - y + 1));
}
else{
puts("-1");
}
}
}
return 0;
}
B. Most socially-distanced subsequence
主要思路:找差值最大的最小数目,找转折点存储即可。
解题思路:
- 首先我们说明一下为什么找转折点,比如 1 3 5 6 ,他的每个的差值是 2 2 1,而且1 和 6的差值就是5,所以中间过程全部可以忽略掉,因此我们找转折点即可
- 除了转折点,我们还需要加上首尾的位置,因为无论如何,首尾的位置都会增加当前消费的总和(每个数值都不一样)
代码:
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
typedef long long ll;
const int N = 100010, M = 200010;
int a[N];
int main(){
int T;
scanf("%d",&T);
while(T--){
int n, m;
scanf("%d%d",&n,&m);
for (int i = 1; i <= n; i++){
scanf("%d",&a[i]);
}
int res = 0;
int x = n + 1, y = 0;
for (int i = 1; i <= n; i++){
if (a[i] % m != 0){
if (x == n + 1) x = i;
if (y < i) y = i;
}
res += a[i];
}
if (res % m != 0) printf("%d\n",n);
else{
if (x != n + 1 && y != 0){
printf("%d\n",n - min(x,n - y + 1));
}
else{
puts("-1");
}
}
}
return 0;
}
C. Ehab and Prefix MEXs
主要思路:存储好没有被赋值的位置,然后当当前的值 > 我们最小赋值的值时,我们进行赋值,其他的随便赋值(1e5 + i)
解题思路:
- 首先我们将每个位置的值都赋为 -1
- 然后我们开一个stack,存储位置。
- 然后我们向stack中存入位置(没有被赋值的位置)
- 当当前值 a[i] > 我们的当前赋值的最小值时,我们进行赋值,然后stack中清除相应位置元素(里面哪一个都可以)
- 最终我们将没有赋值的位置都赋值成 1e5 + i即可,因为不要相同,而且不要超过1e6
代码:
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <stack>
using namespace std;
typedef long long ll;
const int N = 100010, M = 200010;
int a[N], res[N];
stack<int> s;
int main(){
int n;
scanf("%d",&n);
for (int i = 1; i <= n; i++){
scanf("%d",&a[i]);
res[i] = -1;
}
int x = 0;
for (int i = 1; i <= n; i++){
s.push(i);
for (int j = x ; j <= a[i] - 1; j ++){
int t = s.top();
res[t] = j;
s.pop();
}
x = a[i];
}
for (int i = 1; i <= n; i++){
if (res[i] == -1){
printf("%d ",100000 + i);
}
else{
printf("%d ",res[i]);
}
}
puts("");
return 0;
}