“强智杯"2020年湖南省大学生计算机程序设计竞赛

oj: 链接

A.2020

oj: 链接

题意

Bobo有一个只包含数字 0,1, 2 的,长度为 n 的字符串 s1 ... sn。他想选出最多的互不重叠的连续子串,这些子串都是2020。求最多可以选出的子串数量。
形式化的,他想求出最大的 k ,是的存在 k 个下标 i1,...,ik 满足

题解

由于数据过小,直接暴力即可

代码

#include <bits/stdc++.h>
using namespace std;
#define _for(i, a) for(int i = 0, len = a; i < len; ++i)
#define _rep(i, a, b) for(int i = a, len = b; i <= len; ++i)
#define outval(a) cout << "debuging|" << #a << ":" << a << "\n";
#define dg if(debug)
typedef long long LL;
const int inf = 0x3f3f3f3f;
const int maxn = 100005;
int debug = 0;

inline LL read() {
    LL x(0), f(1); char ch(getchar());
    while(ch < '0' || ch > '9') {
        f = -1;
        ch = getchar();
    }
    while(ch >= '0' && ch <= '9') {
        x = x * 10 + ch - '0';
        ch = getchar();
    }
    return x * f;
}

struct poi {

};

char s[maxn];
int n;

void init() {

}

int sol() {
    init();
    scanf("%s", s);
    int ans = 0;
    int n = strlen(s);
    for(int i = 0; i + 3 < n;) {
        if(s[i] == '2' && s[i + 1] == '0' && s[i + 2] == '2' && s[i + 3] == '0') {
            ++ans;
            i += 4;
        }
        else ++i;
    }
    printf("%d\n", ans);
    return 0;
}

int main() {
#ifndef ONLINE_JUDGE
    freopen("in.txt", "r", stdin);
    debug = 1;
#endif
    while(cin>>n) {
        sol();
    }
    return 0;
}

B.2020 vs 2018

oj: 链接

题意

Bobo有一副 n 行 m 列,只包含 '.' 和 'o' 两种字符的字符画,其中 '.' 是背景,'o' 画出了2018或者2020。请识别给出的字符画是2018还是2020的。

题解

只需要判断是否存在由'0'组成的1即可

代码

#include <bits/stdc++.h>
using namespace std;
#define _for(i, a) for(int i = 0, len = a; i < len; ++i)
#define _rep(i, a, b) for(int i = a, len = b; i <= len; ++i)
#define outval(a) cout << "debuging|" << #a << ":" << a << "\n";
#define dg if(debug)
typedef long long LL;
const int inf = 0x3f3f3f3f;
const int maxn = 1005;
int debug = 0;

inline LL read() {
    LL x(0), f(1); char ch(getchar());
    while(ch < '0' || ch > '9') {
        f = -1;
        ch = getchar();
    }
    while(ch >= '0' && ch <= '9') {
        x = x * 10 + ch - '0';
        ch = getchar();
    }
    return x * f;
}

struct poi {

};

int n, m;
char s[57][57];
void init() {
    _rep(i,1,n) scanf("%s",s[i]+1);
    _rep(i,1,n){
        dg outval(i);
        _rep(j,i,n){
            dg outval(j);
            _rep(k,1,m){
                int f=1;
                if(i>1&&s[i-1][k]=='o') continue;
                if(j<n&&s[j+1][k]=='o') continue;
                _rep(l,i,j){
                    if(s[l][k]!='o'){
                        f=0;
                        break;
                    }
                    if(k>1){
                        if(s[l][k-1]=='o'){
                            f=0;
                            break;
                        }
                    }
                    if(k<m){
                        if(s[l][k+1]=='o'){
                            f=0;
                            break;
                        }
                    }
                }
                if(f){
                    puts("2018");
                    return ;
                }
            }
        }
    }
    

    _rep(i,1,m){
        _rep(j,i,m){
            _rep(k,1,n){
                int f=1;
                if(i>1&&s[k][i-1]=='o') continue;
                if(j<m&&s[k][j+1]=='o') continue;
                _rep(l,i,j){
                    if(s[k][l]!='o'){
                        f=0;
                        break;
                    }
                    if(k>1){
                        if(s[k-1][l]=='o'){
                            f=0;
                            break;
                        }
                    }
                    if(k<n){
                        if(s[k+1][l]=='o'){
                            f=0;
                            break;
                        }
                    }
                }
                if(f){
                    puts("2018");
                    return ;
                }
            }
        }
    }
    puts("2020");
}


int main() {
#ifndef ONLINE_JUDGE
    freopen("in.txt", "r", stdin);
    // debug = 1;
#endif
    while(~scanf("%d%d",&n,&m)) init();
    return 0;
}

D.String Commutativity

oj: 链接

题意

有n个字符串s1,...,sn,他想找到对数i <j,其中si + sj = sj + si。注意,a + b表示字符串a和b的串联,即,首先写字符串a,然后写字符串b。例abcd+efg=abcdefg。

题解

如果两个串有相同的最短循环节,则这两个串符合题目要求。用kmp求最短循环节,但kmp求出的最短循环节不一定符合题意,例如aba的最短循环节为ab,而kmp求出的为aba,所以应排除这种情况。即用m%x!=0判断是否最后一个循环节是否完全循环

代码

#include <cstring>
#include <iostream>
#include <cstdio>
#include <fstream>
#include <algorithm>
#include <map>
using namespace std;
const int maxn=1e6+7;
const int INF=0x3f3f3f3f;
#define M 50015
int next1[maxn];
char str[maxn],mo[maxn];
int ans;
map<string,int> mp;
string tran(int x){
    string a;
    for(int i=0;i<x;i++){
        a.push_back(mo[i]);
    }
    return a;
}
void getnext()
{
    int i=0,j=-1,m=strlen(mo);
    while(i<m){
        if(j==-1||mo[i]==mo[j])
            next1[++i]=++j;
        else
            j=next1[j];
    }
}
int main()
{

    int t;
    while(~scanf("%d",&t)){
        mp.clear();
        long long sum=0;
        while(t--){
            ans=0;
            scanf("%s",mo);
            next1[0]=-1;
            getnext();
            int m=strlen(mo);
            int x=m-next1[m];
            if(x<m&&m%x!=0){
                x=m;
            }
            
            //printf("x:%d\n", x);
            string y=tran(x);
            mp[y]++;

        }
        map<string,int>::iterator it;
        it=mp.begin();
        while(it!=mp.end()){
            int n=it->second;
            sum+=1LL*n*(n-1)/2;
            it++;
        }
        printf("%lld\n",sum);
    }
    return 0;
}

G.奇矩阵

oj: 链接

题意

题解

队友写的签到题

代码

#include <bits/stdc++.h>
using namespace std;
#define _for(i, a) for(int i = 0, len = a; i < len; ++i)
#define _rep(i, a, b) for(int i = a, len = b; i <= len; ++i)
#define outval(a) cout << "debuging|" << #a << ":" << a << "\n";
#define dg if(debug)
typedef long long LL;
const int inf = 0x3f3f3f3f;
const int maxn = 1005;
int debug = 0;

inline LL read() {
    LL x(0), f(1); char ch(getchar());
    while(ch < '0' || ch > '9') {
        f = -1;
        ch = getchar();
    }
    while(ch >= '0' && ch <= '9') {
        x = x * 10 + ch - '0';
        ch = getchar();
    }
    return x * f;
}

struct poi {

};

int n, m;
int num[2];

void init() {
    num[0] = num[1] = 0;
}

int sol() {
    init();
    _for(i, n) {
        LL sum = 0;
        _for(j, m) sum += read();
        ++num[sum & 1];
    }
    if(num[0] > 1 || num[1] > 1) return 0;
    return 1;
}

int main() {
#ifndef ONLINE_JUDGE
    freopen("in.txt", "r", stdin);
    debug = 1;
#endif
    while(cin>>n>>m) {
        printf("%s\n", sol() ? "Yes":"No");
    }
    return 0;
}

H.矩阵并

oj: 链接

题意

题解

涛神过的题,完全看不懂

代码

#include <bits/stdc++.h>
using namespace std;
#define _for(i, a) for(int i = 0, len = a; i < len; ++i)
#define _rep(i, a, b) for(int i = a, len = b; i <= len; ++i)
#define outval(a) cout << "debuging|" << #a << ":" << a << "\n";
#define dg if(debug)
typedef long long LL;
const int inf = 0x3f3f3f3f;
const double eps = 1e-8;
const int maxn = 1005;
const LL mod = 1000000007;
int debug = 0;

inline LL read() {
    LL x(0), f(1); char ch(getchar());
    while(ch < '0' || ch > '9') {
        if(ch == '-') f = -1;
        ch = getchar();
    }
    while(ch >= '0' && ch <= '9') {
        x = x * 10 + ch - '0';
        ch = getchar();
    }
    return x * f;
}

struct poi {
    
};

LL a, b;

void exgcd(LL a, LL b, LL &g, LL &x, LL &y) {
    if (!b) {
        g = a;
        x = 1;
        y = 0;
    } else {
        exgcd(b, a % b, g, y, x);
        y -= x * (a / b);
    }
}
LL inv(LL x, LL mod) {
    LL a, k, g;
    exgcd(x, mod, g, a, k);
    if(a < 0) a += mod;
    return a;
}

LL getval(LL a, LL b) {
    LL ans = 0;
    ans += a * a % mod * b % mod * b;
    ans += a * b % mod * b % mod;
    ans += a * a % mod * b % mod;
    ans += a * b % mod;
    ans %= mod;
    ans *= inv(4, mod);
    return ans % mod;
}

int sol() {
    LL x = read(), xx = read(), y = read(), yy = read();
    LL ans = 0;
    ans += getval(a, b);
    dg printf("累积:%lld\n", getval(a, b));

    LL w1 = max(0LL, min(b, yy) - y);
    LL box1 = w1 * (w1 + 1) % mod * inv(2, mod) % mod * max(0LL, a - xx) % mod * (xx - x) % mod;
    LL w2 = max(0LL, min(a, xx) - x);
    if(a < x) w2 = 0;
    dg printf("w1:%lld\tw2:%lld\n", w1, w2);
    LL box2 = w2 * (w2 + 1) % mod * inv(2, mod) % mod * max(0LL, b - yy) % mod * (yy - y) % mod;
    LL box3 = max(0LL, a - xx) * max(0LL, b - yy) % mod * (xx - x) % mod * (yy - y) % mod;
    LL ans2 = box1 + box2 + box3 + getval(max(0LL, min(a, xx) - x), max(0LL, min(b, yy) - y)); ans2 %= mod;
    dg printf("box1:%lld\tbox2:%lld\tbox3:%lld\n", box1, box2, box3);
    dg printf("减去:%lld\n", ans2);

    ans += mod - ans2;
    LL ans3 = (xx - x) * (yy - y) % mod * a % mod * b % mod;
    ans += ans3;
    dg printf("额外:%lld\n", ans3);

    ans %= mod;
    printf("%lld\n", ans);
    return 0;
}

int main() {
#ifndef ONLINE_JUDGE
    freopen("in.txt", "r", stdin);
    // debug = 1;
#endif
    while(~scanf("%lld%lld", &a, &b)) {
        sol();
    }
    return 0;
}

I.共线点

oj: 链接

题意

题解

模板题

代码

#include <bits/stdc++.h>
using namespace std;
#define _for(i, a) for(int i = 0, len = a; i < len; ++i)
#define _rep(i, a, b) for(int i = a, len = b; i <= len; ++i)
#define outval(a) cout << "debuging|" << #a << ":" << a << "\n";
#define dg if(debug)
typedef long long LL;
const int inf = 0x3f3f3f3f;
const double eps = 1e-8;
const int maxn = 1005;
int debug = 0;

inline LL read() {
    LL x(0), f(1); char ch(getchar());
    while(ch < '0' || ch > '9') {
        f = -1;
        ch = getchar();
    }
    while(ch >= '0' && ch <= '9') {
        x = x * 10 + ch - '0';
        ch = getchar();
    }
    return x * f;
}

struct poi {
    int a, b, y;
    bool operator<(const poi &b) const {
        if(y != b.y) return y < b.y;
        else if(a != b.a) return a < b.a;
        else return this->b < b.b;
    }
};

poi a[3];

void init() {

}

int sol() {
    _rep(i, 1, 2) {
        int aa, bb, yy;
        scanf("%d%d%d", &aa, &bb, &yy);
        a[i] = {aa, bb, yy};
    }
    sort(a, a + 3);
    double x1 = 1.0 * (a[2].a - a[0].a) / (a[2].y - a[0].y) * (a[1].y - a[0].y) + a[0].a;
    double x2 = 1.0 * (a[2].b - a[0].b) / (a[2].y - a[0].y) * (a[1].y - a[0].y) + a[0].b;
    dg printf("xx1:%.2f\txx2:%.2f\n", x1, x2);
    if(x1 - eps <= a[1].b && x2 + eps >= a[1].a) return 1;
    return 0;
}

int main() {
#ifndef ONLINE_JUDGE
    freopen("in.txt", "r", stdin);
    debug = 1;
#endif
    int aa, bb, yy;
    while(~scanf("%d%d%d", &aa, &bb, &yy)) {
        a[0] = {aa, bb, yy};
        printf("%s\n", sol () ?"Yes":"No");
    }
    return 0;
}
posted @ 2021-03-10 19:42  指尖跳动的电光  阅读(220)  评论(0编辑  收藏  举报