CF_#324(Div.2)

感觉最近做题太少,昨晚上一时兴起注册了晚上十二点半的CF,做到了两点半,没想到最后把C绝杀了,rating上升了一些,还不错。早上起来把D也过了,稍微总结一下。

A. Olesya and Rodion
time limit per test
1 second
memory limit per test
256 megabytes
input
standard input
output
standard output

Olesya loves numbers consisting of n digits, and Rodion only likes numbers that are divisible by t. Find some number that satisfies both of them.

Your task is: given the n and t print an integer strictly larger than zero consisting of n digits that is divisible by t. If such number doesn't exist, print  - 1.

Input

The single line contains two numbers, n and t (1 ≤ n ≤ 1002 ≤ t ≤ 10) — the length of the number and the number it should be divisible by.

Output

Print one such positive number without leading zeroes, — the answer to the problem, or  - 1, if such number doesn't exist. If there are multiple possible answers, you are allowed to print any of them.

Sample test(s)
input
3 2
output
712


题解:

让你输出一个能被t整除的n位数字,刚开始看样例吓到了,这么大怎么去存,没有思路,后来慢慢往t突破,t的范围2~10,想找能被这些数整除的数的性质,自己凑一个数。分情况讨论交了一遍后才发现自己傻逼了,干嘛不每一位都是t呐?只有10的时候另外讨论。。。马上改代码核心不到10行,又因为1,10这样的-1的情况没有讨论wa了一次,就这样A跌跌撞撞过了。

代码实现:

#include <bits/stdc++.h>

using namespace std;

const int MAX = 110;

int N,T;
int main()
{
    scanf("%d%d",&N,&T);
    if( N == 1 && T == 10 ){
        printf("-1\n");
        return 0;
    }
    if( T == 10 ){
        for( int i = 0; i < N-1; i++ ){
            printf("1");
        }
        printf("0\n");
    }
    else{
        for( int i = 0; i < N; i++ ){
            printf("%d",T);
        }
        printf("\n");
    }
    return 0;
}


B. Kolya and Tanya
time limit per test
1 second
memory limit per test
256 megabytes
input
standard input
output
standard output

Kolya loves putting gnomes at the circle table and giving them coins, and Tanya loves studying triplets of gnomes, sitting in the vertexes of an equilateral triangle.

More formally, there are 3n gnomes sitting in a circle. Each gnome can have from 1 to 3 coins. Let's number the places in the order they occur in the circle by numbers from 0 to 3n - 1, let the gnome sitting on the i-th place have ai coins. If there is an integer i (0 ≤ i < n) such that ai + ai + n + ai + 2n ≠ 6, then Tanya is satisfied.

Count the number of ways to choose ai so that Tanya is satisfied. As there can be many ways of distributing coins, print the remainder of this number modulo 109 + 7. Two ways, a and b, are considered distinct if there is index i (0 ≤ i < 3n), such thatai ≠ bi (that is, some gnome got different number of coins in these two ways).

Input

A single line contains number n (1 ≤ n ≤ 105) — the number of the gnomes divided by three.

Output

Print a single number — the remainder of the number of variants of distributing coins that satisfy Tanya modulo 109 + 7.

Sample test(s)
input
1
output
20
input
2
output
680
Note

20 ways for n = 1 (gnome with index 0 sits on the top of the triangle, gnome 1 on the right vertex, gnome 2 on the left vertex):


题解:

这道题还是比较裸的,就是一个简单的动态规划,找到递推式就很好做了,一遍过。

代码实现:

#include <bits/stdc++.h>
#define LL long long

using namespace std;

const int MAX = 100010;
const int mod = 1000000000+7;

int N;
LL dp[MAX];
LL Time[MAX];
int main()
{
    scanf("%d",&N);
    memset(dp,0,sizeof(dp));
    memset(Time,0,sizeof(Time));
    dp[1] = 20;
    Time[0] = 1;
    Time[1] = 7;
    for( int i = 2; i <= N; i++ ){
        dp[i] = (27*dp[i-1]%mod+20*Time[i-1]%mod)%mod;
        Time[i] = Time[i-1]*7%mod;
    }
    printf("%I64d\n",dp[N]);
    return 0;
}


C. Marina and Vasya
time limit per test
1 second
memory limit per test
256 megabytes
input
standard input
output
standard output

Marina loves strings of the same length and Vasya loves when there is a third string, different from them in exactly tcharacters. Help Vasya find at least one such string.

More formally, you are given two strings s1s2 of length n and number t. Let's denote as f(a, b) the number of characters in which strings a and b are different. Then your task will be to find any string s3 of length n, such that f(s1, s3) = f(s2, s3) = t. If there is no such string, print  - 1.

Input

The first line contains two integers n and t (1 ≤ n ≤ 1050 ≤ t ≤ n).

The second line contains string s1 of length n, consisting of lowercase English letters.

The third line contain string s2 of length n, consisting of lowercase English letters.

Output

Print a string of length n, differing from string s1 and from s2 in exactly t characters. Your string should consist only from lowercase English letters. If such string doesn't exist, print -1.

Sample test(s)
input
3 2
abc
xyc
output
ayd
input
1 0
c
b
output
-1


题解:

自已眼看这道题感觉在那里做过。。。有两个字符串,求第三个字符串使其与前两个串的差异度都是t。那关键点肯定是串1和串2的相似度啊。分情况讨论把,看看目标差异度t和str1,str2固有差异度x之间的相对关系。

第一种:t<=len && t>=x;

这时候首先保证str1,str2不同时str3也和他们都不同,剩下配上几个他们两个相同的情况。

第二种:t >= x/2;

为什么是len/2?因为这个时候他们要重叠一部分,也就是说在str1和str2不相同的那一段上,str3要分别有x-t的长度和str1,str2一样。另外t = x/2 的时候要另外讨论,毕竟x的奇偶性不太清楚,多一个都不行。

剩下的就是不符合的情况;

最后5分钟绝杀,好险好险。。。

代码实现:

#include <bits/stdc++.h>

using namespace std;

const int MAX = 100010;

int N,T;
int cnt;
int len;
bool flag;
int tag[MAX];
char str1[MAX];
char str2[MAX];
char str3[MAX];
char get(char a,char b);
int main()
{
    scanf("%d%d",&N,&T);
    scanf("%s",str1);
    scanf("%s",str2);
    flag = true;
    cnt = 0;
    len = strlen(str1);
    memset(tag,0,sizeof(tag));
    for( int i = 0; i < len; i++ ){
        if( str1[i] != str2[i] ){
            cnt++;
            tag[i] = 1;
        }
    }
    if( T>=cnt && T<=len ){
        for( int i = 0; i < len; i++ ){
            if( tag[i] == 1 ){
                str3[i] = get(str1[i],str2[i]);
                T--;
            }
            else{
                str3[i] = str1[i];
            }
        }
        for( int i = 0; i < len; i++ ){
            if( T == 0 ){
                break;
            }
            if( tag[i] == 0 ){
                str3[i] = get(str1[i],str2[i]);
                T--;
            }
        }
    }
    else if( T>=cnt/2 ){
        if( T == cnt/2 ){
            if( cnt%2 == 0 ){
                int tmp = cnt/2;
                int pos = 0;
                while( tmp ){
                    str3[pos] = str1[pos];
                    if( tag[pos] == 1 ){
                        tmp--;
                    }
                    pos++;
                }
                tmp = cnt/2;
                while( tmp ){
                    str3[pos] = str2[pos];
                    if( tag[pos] == 1 ){
                        tmp--;
                    }
                    pos++;
                }
                while( pos < len ){
                    str3[pos] = str1[pos];
                    pos++;
                }
            }
            else{
                flag = false;
            }
        }
        else{
            int tmp = cnt-T;
            int pos = 0;
            while( tmp ){
                str3[pos] = str1[pos];
                if( tag[pos] == 1 ){
                    tmp--;
                }
                pos++;
            }
            tmp = cnt-T;
            while( tmp ){
                str3[pos] = str2[pos];
                if( tag[pos] == 1 ){
                    tmp--;
                }
                pos++;
            }
            while( pos < len ){
                str3[pos] = str1[pos];
                if( tag[pos] == 1 ){
                    str3[pos] = get(str1[pos],str2[pos]);
                }
                pos++;
            }
        }
    }
    else{
        flag = false;
    }
    if( flag == false ){
        printf("-1\n");
    }
    else{
        printf("%s\n",str3);
    }
    return 0;
}

char get(char a,char b){
    int na = (int)a;
    int nb = (int)b;
    if( na == nb ){
        if( a != 'a' ){
            return char(na-1);
        }
        else{
            return char(na+1);
        }
    }
    else{
        if( na < nb ){
            swap(na,nb);
        }
        if( na-nb > 1 ){
            return char(na-1);
        }
        else{
            if( a!='a' && b!='a' ){
                return char(nb-1);
            }
            else{
                return char(na+1);
            }
        }
    }
}

D. Dima and Lisa
time limit per test
1 second
memory limit per test
256 megabytes
input
standard input
output
standard output

Dima loves representing an odd number as the sum of multiple primes, and Lisa loves it when there are at most three primes. Help them to represent the given number as the sum of at most than three primes.

More formally, you are given an odd numer n. Find a set of numbers pi (1 ≤ i ≤ k), such that

  1. 1 ≤ k ≤ 3
  2. pi is a prime

The numbers pi do not necessarily have to be distinct. It is guaranteed that at least one possible solution exists.

Input

The single line contains an odd number n (3 ≤ n < 109).

Output

In the first line print k (1 ≤ k ≤ 3), showing how many numbers are in the representation you found.

In the second line print numbers pi in any order. If there are multiple possible solutions, you can print any of them.

Sample test(s)
input
27
output
3
5 11 11
Note

A prime is an integer strictly larger than one that is divisible only by one and by itself.


题解:

把一个大奇数分成最多三个质数的和,我靠,像不像哥德巴赫猜想??然并不会啊,毕竟不是数学专业,竟是硬伤,暴力筛素数然后深搜试了一下,内存和时间各爆了一回。后来看了一下数据,如果是暴力搜的话前一个或两个素数应该不会太大的,超时和爆内存都是在筛法上,改成了10^3。吓,竟然过了。但是后来看了看别人的代码,果然是得先推一下再去解的。。。。先冷静一下吧。

代码实现:

#include <bits/stdc++.h>

using namespace std;

const int MAX = 1010;

int N;
int sum;
int len;
bool flag;
int save[3];
int prime[MAX];
bool if_prime[MAX];
int pre(int num);
bool ifp(int n);
void dfs(int num,int pos,int tag);
int main()
{
    sum = pre(1000);
    while( scanf("%d",&N) != EOF ){
        len = 0;
        flag = false;
        dfs(N,0,0);
        printf("%d\n",len);
        for( int i = 0; i < len; i++ ){
            printf("%d",save[i]);
            if( i != len-1 ){
                printf(" ");
            }
            else{
                printf("\n");
            }
        }
    }
    return 0;
}

int pre(int num){
    int pos = 0;
    for( int i = 1; i <= num; i++ ){
        if_prime[i] = true;
    }
    memset(prime,0,sizeof(prime));
    for( int i = 2; i <= num; i++ ){
        if( if_prime[i] == false ){
            continue;
        }
        prime[pos++] = i;
        for( int j=2*i; j <= num; j+=i ){
            if_prime[j] = false;
        }
    }
    return pos;
}

void dfs(int num,int pos,int tag){
    if( pos >= 3 ){
        return ;
    }
    if( ifp(num) ){
        save[pos] = num;
        pos++;
        len = pos;
        flag = true;
        return ;
    }
    for( int i = tag; tag < sum; i++ ){
        if( prime[i] > num ){
            break;
        }
        save[pos] = prime[i];
        dfs(num-prime[i],pos+1,i);
        if( flag == true ){
            break;
        }
    }
    return ;
}

bool ifp(int n){
    for( int i = 0; i < sum; i++ ){
        if( n%prime[i] == 0 ){
            return false;
        }
        if( prime[i]*prime[i] > n ){
            break;
        }
    }
    return true;
}

再贴一个牛逼点的代码。。。T T

#include<bits/stdc++.h>
#define f(i,a,b) for(i=a;i<b;i++)
using namespace std;
int prime(int n)
{
    for(int i=2;i*i<=n;i++)if(n%i==0)return 0;
    return 1;
}
int main()
{
    int n,i;
    cin>>n;
    if(prime(n)){printf("1\n%d",n);return 0;}
    printf("3\n3 ");
    n-=3;
    for(i=3;;i+=2)if(prime(i)&&prime(n-i)){printf("%d %d",i,n-i);return 0;}
}




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值