AtCoder Regular Contest 077

来源:互联网 发布:自制海报软件 编辑:程序博客网 时间:2024/05/16 15:07

C

题意:一个序列a,对序列a进行操作,每次吧序列a的第一个元素插入序列b的末端,然后反转序列b,问最后的到的序列b

思路:由题可以反向推理,假设已经有了序列b,然后反转序列b,此时序列b中bn的元素等于an, 去掉bn,然后再反转序列b,此时b序列中末端是b1,可知b1等于an-1,继续下去即可。

    #include <cstdio>    #include <cstring>    #include <cmath>    #include <cstdlib>    #include <ctime>    #include <iostream>    #include <algorithm>    #include <sstream>    #include <string>    #include <vector>    #include <queue>    #include <stack>    #include <map>    #include <set>    #include <utility>         using namespace std;    #define LL long long    #define pb push_back    #define mk make_pair    #define mst(a, b)memset(a, b, sizeof a)    #define REP(i, x, n)for(int i = x; i <= n; ++i)    const int qq = 2e5 + 10;    int a[qq], b[qq];         int main(){    int n;scanf("%d", &n);    REP(i, 1, n){    scanf("%d", a + i);    }    int l = 1, r = n;    int cnt = 1, p = n;    for(int i = n; i >= 1; --i){    if(cnt & 1)b[l++] = a[p--];    elseb[r--] = a[p--];    cnt++;    }    REP(i, 1, n - 1){    printf("%d ", b[i]);    }    printf("%d\n", b[n]);    return 0;    }

D

题意:给出一个有n + 1元素的序列,要你找出有多少种不相同的子序列

思路:注意到只有一个数字会出现两次,反向思维先得到Cn,k 然后我们减去重复的,

        比如 2 3 1 4 5 1 6

可知如果某个序列包含了1 1,那么前后两个1是互不影响的。

如果同时不包含 1 1,那么也都不会算重

只包含一个1的情况下,并且不包含两个1之间元素的序列是会有重复,比如选第一个1时, 2 3 1,选第二个1时, 2 3 1。

最后得到Cn,k - Cn - d(两个1之间的距离),k - 1。

注意的用逆元,直接算mod的结果是不对的

#include <cstdio>#include <cstring>#include <map>#include <algorithm>#include <iostream>#include <vector>using namespace std;#define LL long long#define pb push_back#define mk make_pair#define pill pair<int, int>#define mst(a, b)memset(a, b, sizeof a)#define REP(i, x, n)for(int i = x; i <= n; ++i)const int MOD = 1e9 + 7;const int qq = 2e5 + 10;int num[qq];LL inv[qq];map<int, int> mp;LL Power(LL x, LL t){LL ret = 1;while(t > 0){if(t & 1)ret = (ret * x) % MOD;x = (x * x) % MOD;t >>= 1;}return ret;}LL Calc(int a, int b){if(a < b)return 0;return inv[a] * Power(inv[b], MOD - 2) % MOD * Power(inv[a - b], MOD - 2) % MOD;}int main(){LL n;scanf("%lld", &n);bool f = false;int l, r;REP(i, 1, n + 1){int x;scanf("%d", &x);num[x]++;if(!f){if(num[x] == 2){l = mp[x];r = i;f = true;}}mp[x] = i;}++n;inv[0] = 1LL;REP(i, 1, n){inv[i] = inv[i - 1] * (LL)i % MOD;}REP(i, 1, n){printf("%lld\n", (((Calc(n, i) - Calc(n - r + l - 1, i - 1)) % MOD + MOD) % MOD));}return 0;}


原创粉丝点击