2019 浙江省赛 ACM 部分题解(E H I K)

练习 链接。

E Sequence in the Pocket
大意 :给定n个数,每次可以选定一个数放到这n个数的最前面,问 经过最少多少次 操作 可以形成一个 严格非递减 的序列(既在每一个数的右侧都不会出现比他小的数)。
思路 :
从右向左看,先找到最大的数,然后找到次大的,再找第三大的。。。一直找到最左端 这是会找到 第 cnt 大的数,输出n-cnt 即可。

DreamGrid has just found an integer sequence in his right pocket. As DreamGrid is bored, he decides to play with the sequence. He can perform the following operation any number of times (including zero time): select an element and move it to the beginning of the sequence.

What’s the minimum number of operations needed to make the sequence non-decreasing?

Input

There are multiple test cases. The first line of the input contains an integer , indicating the number of test cases. For each test case:

The first line contains an integer (), indicating the length of the sequence.

The second line contains integers (), indicating the given sequence.

It’s guaranteed that the sum of of all test cases will not exceed .

Output

For each test case output one line containing one integer, indicating the answer.

Sample Input
2
4
1 3 2 4
5
2 3 3 5 5

Sample Output
2
0

Hint

For the first sample test case, move the 3rd element to the front (so the sequence become {2, 1, 3, 4}), then move the 2nd element to the front (so the sequence become {1, 2, 3, 4}). Now the sequence is non-decreasing.

For the second sample test case, as the sequence is already sorted, no operation is needed.

AC 代码:

#include <cstdio>
#include <cstring>
#include <string>
#include <iostream>
#include <algorithm>
#define For(i,L,R) for(int i=L;i<=R;i++)
using namespace std;
const int N = 1e5+100;
int a[N],b[N];
bool cmp(int u,int v){
    return u>v;
}
int main()
{
    int T,n;
    scanf("%d",&T);
    while(T--){
        scanf("%d",&n);
        For(i,1,n){
            scanf("%d",&a[i]);
            b[i] = a[i];
        }
        sort(b+1,b+1+n,cmp);
        /*
        for(int i=1;i<=n;i++){
            printf("%d%c",b[i],i==n?'\n':' ');
        }
         */
        int cnt = 1;
        for(int i=n;i>=1;i--){
            if( b[cnt] == a[i] ){
                cnt++;
                //printf("%d , ( %d ) = %d \n",b[i],i,a[i]);
            }
        }
        printf("%d\n",n-cnt+1);
    }
    return 0;
}

F Fibonacci in the Pocket

题意及思路: 给定两个数 a,b; 还有一个序列 f : :f1=1 ,f2=1 ,f3=2 ,f4=3 ,f5=5 ,f6=8 …i>2 fi=f(i-1)+f(i-2);
问你 从f(a) 到 f(b)中所有数的累加和 是奇数还是 偶数。 数据比较大 10的10000次方 要用大数。
思路就是直接写 找到 为0的情况 剩余的就是为1的情况 详情见代码(学长打的,没学java,不会大数。。。)。

DreamGrid has just found a Fibonacci sequence and two integers and in his right pocket, where indicates the -th element in the Fibonacci sequence.

Please tell DreamGrid if is even or is odd.

Recall that a Fibonacci sequence is an infinite sequence which satisfies , and for all .

Input

There are multiple test cases. The first line of the input contains an integer (about 100), indicating the number of test cases. For each test case:

The first and only line contains two integers and (). Their meanings are described above.

Output

For each test case output one line. If is even output “0” (without quotes); If is odd output “1” (without quotes).

Sample Input
6
1 2
1 3
1 4
1 5
123456 12345678987654321
123 20190427201904272019042720190427

Sample Output
0
0
1
0
0
1

Hint

The first few elements of the Fibonacci sequence are:f1=1 ,f2=1 ,f3=2 ,f4=3 ,f5=5 ,f6=8 …i>2 fi=f(i-1)+f(i-2);
AC代码:

import java.math.BigInteger;
import java.util.Scanner;
public class Main {
    public static void main(String []args) {
        Scanner sc = new Scanner(System.in);
        int T = sc.nextInt();
        while (T > 0) {
            T--;
            BigInteger one = new BigInteger("1");
            BigInteger two = new BigInteger("2");
            BigInteger three = new BigInteger("3");
            BigInteger zero = new BigInteger("0");
            BigInteger a = sc.nextBigInteger();
            BigInteger b = sc.nextBigInteger();
            BigInteger d = b.subtract(a);
            d = d.add(one);
            if( d.mod(three).equals(zero)){
                System.out.println("0");
            }else if( d.mod(three).equals(two) && a.mod(three).equals(one) ){
                System.out.println("0");
            }else if( d.mod(three).equals(one) && a.mod(three).equals(zero)){
                System.out.println("0");
            }else{
                System.out.println("1");
            }
        }
    }
}

H Singing Everywhere

题意: 若 an>a(n-1) && an >a(n+1) 则在n点 为一个峰。
给定一序列 n个数,最多可以删掉一个数,问经过该操作后,剩余的峰的最小数量。
思路: 无论如何 经过一次操作只会出现3个情况 峰的数量-0峰的数量-1,峰的数量-2. 训练时 我只想到两种情况还以为是对的,,,还好不是我实现这个题,否则可能又要被卡住。。。。。

Baobao loves singing very much and he really enjoys a game called Singing Everywhere, which allows players to sing and scores the players according to their performance.

Consider the song performed by Baobao as an integer sequence , where indicates the -th note in the song. We say a note is a “voice crack” if , and . The more voice cracks BaoBao sings, the lower score he gets.

To get a higher score, BaoBao decides to delete at most one note in the song. What’s the minimum number of times BaoBao sings a voice crack after this operation?

Input

There are multiple test cases. The first line of the input contains an integer (about 100), indicating the number of test cases. For each test case:

The first line contains one integer (), indicating the length of the song.

The second line contains integers (), indicating the song performed by BaoBao.

It’s guaranteed that at most 5 test cases have .

Output

For each test case output one line containing one integer, indicating the answer.

Sample Input
3
6
1 1 4 5 1 4
7
1 9 1 9 8 1 0
10
2 1 4 7 4 8 3 6 4 7

Sample Output
1
0
2

Hint

For the first sample test case, BaoBao does not need to delete a note. Because if he deletes no note, he will sing 1 voice crack (the 4th note), and no matter which note he deletes, he will also always sing 1 voice crack.

For the second sample test case, BaoBao can delete the 3rd note, and no voice cracks will be performed. Yay!

For the third sample test case, BaoBao can delete the 4th note, so that only 2 voice cracks will be performed (4 8 3 and 3 6 4).

学长AC代码:

#include <cstdio>
#include <cstring>
#include <string>
#include <iostream>
#include <algorithm>
#define For(i,L,R) for(int i=L;i<=R;i++)
using namespace std;
const int N = 1e5+100;
int a[N],L[N],R[N],St[N],vis[N];
int main()
{
    int T,n;
    scanf("%d",&T);
    while(T--){
        memset(vis,0,sizeof(vis));
        scanf("%d",&n);
        int top=0,ans=0,f=0;
        For(i,1,n){
            scanf("%d",&a[i]);
        }
        a[0] = a[n+1] = a[n+2] = 0x7fffffff;
        For(i,2,n-1){
            if( a[i-1]<a[i] && a[i] > a[i+1] ){
                vis[i]=1;
                ans++;
            }
        }
        For(i,1,n){
            if( vis[i-1] == 1 && vis[i+1] == 1){
                if( a[i-1] == a[i+1] )
                    f = max(f,2);
                else {
                    f = max(f,1);
                }
            }
            if( 2<=i && i<=n && vis[i] ){
                if(!(a[i-2] < a[i-1] && a[i-1]>a[i+1])
                &&  !(a[i-1] < a[i+1] && a[i+1]>a[i+2])
                ){
                    f = max(f,1);
                }
            }
        }
        ans = ans - f;
        printf("%d\n",ans);
    }
    return 0;
}

K Strings in the Pocket
吐槽 : 个人感觉最可惜的一道题 3.00开始怼一个小时基本ok了,少了一个特判0的情况,一直以为是数组初始化 或大小 的 问题,白怼了两个多小时 真是心态爆炸 后来学姐想到特判 0的情况 可是心态爆炸了 没写全。。。。。
下次一定注意心态。。。。
题意:
给定两个字符串 a,b; 每次操作 可以将一个区间 [a,b] 内所有数 左右调换 ,问最多有多少种方法。
思路:
分开处理
如果两个字符串不同的话 :先判断是否可以 ,若不可以相同 就是 0 。昨天就是这里没想全。。。
若可以,就找到第一个不同的数的位置a,最后一个不同的数的位置b,然后a向左慢慢偏 移,b向右慢慢偏移,直到停止。
如果两个字符串相同的话,就以每一个字符都当作中心来查看,这时 如果 出现连续多个相同的字符串如aaaaa 可以利用等差数列求和公式来维护 5个a的维护值为(5+1)
5 / 2 =15;
*

题目数据
AC代码:

#include <map>
#include <set>
#include <cstdio>
#include <cstring>
#include <string>
#include <iostream>
#include <algorithm>
#define For(i,L,R) for(int i=L;i<=R;i++)
using namespace std;
const int N = 3e6+1000;
char str1[N],str2[N];
int main()
{
    long long int T,n;
    scanf("%lld",&T);
    while(T--){
        long long int a,b;
        a=b=0;
        scanf("%s",str1+1);
        scanf("%s",str2+1);
        long long int n=strlen(str1+1);
        for(long long int i=1;i<=n;i++)
        {
            if(str1[i]-str2[i]!=0)
            {
                a=i;
                break;
            }
        }
        for(long long int i=n;i>=1;i--)
        {
            if(str1[i]-str2[i]!=0)
            {
                b=i;
                break;
            }
        }
        long long int flag=0;
        if(a!=0)
        {
            for(long long int i=0;;i++)
            {
               // printf("1 %lld\n",i);
                if(a+i>b&&b-i<a)
                    break;
                if(str1[a+i]-str2[b-i]!=0||str1[b-i]-str2[a+i]!=0)
                {
                //    printf("%c %c !! %c %c\n",str1[a+i],str2[b-i],str1[b-i],str2[a+i]);
                    flag=1;
                    break;
                }
            }
            if(flag==1)
            {
                printf("0\n");
                continue;
            }
        }
        if(a==0||b==0)
        {
            long long int ans=0;
            for(long long int i=1;i<=n;i++)
            {
                long long int j;
                for(j=i;j<=n;j++)
                {
                    if(str1[j+1]-str1[i]!=0)
                        break;
                }
                long long int d=j-i+1;
                ans=ans+(d*(d+1))/2;
                long long int l,r,cnt;
                l=i-1,r=j+1;
                for(cnt=0;;)
                {
                    if(l-cnt==0||r+cnt==n+1)
                        break;
                    if(str1[l-cnt]-str2[r+cnt]!=0)
                        break;
                    cnt++;
                }
                ans=ans+cnt;
                i=j;
            }
            printf("%lld\n",ans);
        }
        else
        {
            long long int i;
            for(i=1;;)
            {
                if(a-i==0||b+i==n+1)
                    break;
                if(str1[a-i]-str1[i+b]!=0)
                    break;
                i++;
            }
            printf("%lld\n",i);
        }
    }
    return 0;
}






发布了18 篇原创文章 · 获赞 7 · 访问量 991

猜你喜欢

转载自blog.csdn.net/qq_43559193/article/details/89632502