zoukankan      html  css  js  c++  java
  • 2019 China Collegiate Programming Contest Qinhuangdao Onsite

    Contest Info


    [Practice Link](https://codeforces.com/gym/102361)
    Solved A B C D E F G H I J K L
    5/12 O - - O - O - - - O Ø -
    • O 在比赛中通过
    • Ø 赛后通过
    • ! 尝试了但是失败了
    • - 没有尝试

    Solutions


    A. Angle Beats

    题意:
    给出(n)个点,每次询问再给出一个点,询问(n)个点中与当前这个点构成直角三角形的方案数。

    D. Decimal

    题意:
    给出一个(n),判断(frac{1}{n})是否是一个无限循环小数。

    思路:
    如果(n)的质因子分解是(2^x5^y)那么不是无限循环

    代码:

    view code
    #include <bits/stdc++.h>
    #define debug(...) { printf("#  "); printf(__VA_ARGS__); puts(""); }
    #define fi first
    #define se second
    #define endl "
    " 
    using namespace std;
    using db = double;
    using ll = long long;
    using ull = unsigned long long; 
    using pII = pair <int, int>;
    using pLL = pair <ll, ll>;
    constexpr int mod = 1e9 + 7;
    template <class T1, class T2> inline void chadd(T1 &x, T2 y) { x += y; while (x >= mod) x -= mod; while (x < 0) x += mod; } 
    template <class T1, class T2> inline void chmax(T1 &x, T2 y) { if (x < y) x = y; }
    template <class T1, class T2> inline void chmin(T1 &x, T2 y) { if (x > y) x = y; }
    inline int rd() { int x; cin >> x; return x; }
    template <class T> inline void rd(T &x) { cin >> x; }
    template <class T> inline void rd(vector <T> &vec) { for (auto &it : vec) cin >> it; }
    inline void pt() { cout << endl; }
    template <class T, class... Ts> void pt(const T& arg, const Ts&... args) { cout << arg << " "; pt(args...); }
    template <class T> inline void pt(const T &s) { cout << s << "
    "; }
    template <class T> inline void pt(const vector <T> &vec) { for (auto &it : vec) cout << it << " "; cout << endl; } 
    ll gcd(ll a, ll b) { return b ? gcd(b, a % b) : a; }
    inline ll qpow(ll base, ll n) { ll res = 1; while (n) { if (n & 1) res = res * base % mod; base = base * base % mod; n >>= 1; } return res; }
    constexpr int N = 1e5 + 10;
    int n; 
    void run() {
    	cin >> n;
    	while (n % 2 == 0) n /= 2;
    	while (n % 5 == 0) n /= 5;
    	if (n == 1) pt("No");
    	else pt("Yes");
    }
    
    int main() {
    	ios::sync_with_stdio(false);
    	cin.tie(nullptr); cout.tie(nullptr);
    	cout << fixed << setprecision(20);
    	int _T; cin >> _T;
    	while (_T--) run();
    	return 0;
    }
    

    F. Forest Program

    题意:
    给出一个无向图,每条边最多存在于一个环中,问多少种移除边的方案使得剩下的每一个连通块都是一棵树

    思路:
    一个环,这个环上至少要切一条边,其他边任意切不切。
    注意刚开始给出的可能不是连通图。

    代码:

    view code
    #include <bits/stdc++.h>
    using namespace std;
    using ll = long long; 
    const int N = 5e5 + 10;
    const ll mod = 998244353;
    int n, m, bit[N];
    vector <vector<int>> G;
    int dep[N], tot, vis[N], Insta[N]; ll res;
    void dfs(int u, int pre) {
    	vis[u] = 1;
    	Insta[u] = 1;
    	for (auto &v : G[u]) if (v != pre) {   
    		if (Insta[v]) { 
    			tot -= dep[u] - dep[v] + 1; 
    			res = 1ll * res * (bit[dep[u] - dep[v] + 1] - 1) % mod;
    			res %= mod;
    		}
    		if (!vis[v]) {
    			dep[v] = dep[u] + 1;
    			dfs(v, u);
    		}
    	}
    	Insta[u] = 0;
    }
     
    int main() {
    	bit[0] = 1;
    	for (int i = 1; i < N; ++i) bit[i] = 1ll * bit[i - 1] * 2 % mod;
    	while (scanf("%d%d", &n, &m) != EOF) {
    		G.clear(); G.resize(n + 1);
    		for (int i = 1; i <= n; ++i) dep[i] = vis[i] = Insta[i] = 0;
    		for (int i = 1, u, v; i <= m; ++i) {
    			scanf("%d%d", &u, &v);
    			G[u].push_back(v);
    			G[v].push_back(u);
    		}
    		tot = m; res = 1; 
    		for (int i = 1; i <= n; ++i) if (!vis[i]) dfs(i, i);
    		res = 1ll * res * bit[tot] % mod;
    		res = (res + mod) % mod;
    		printf("%lld
    ", res);
    	}
    	return 0;
    }
    

    I. Invoker

    题意:
    每种技能需要三种属性,三个属性被按下就可以触发,而顺序不重要。
    但是每次只能保留三个属性,按下第四个的时候第一个会被移除。
    现在给出一个需要使用的技能表,询问怎样按键使得按顺序出发这些技能并且按下的次数最少。

    思路:
    考虑每种技能最多只有六种排列状态,那么(f[i][S])表示前(i)个技能,当前排列状态为(S)的最少按键数。

    代码:

    view code
    #include <bits/stdc++.h>
    using namespace std;
    
    const int N = 1e5 + 10;
    char s[N]; int n;
    map <string, int> f[2];
    map <char, string> mp;
    
    int main() {
        mp['Y'] = "QQQ";
        mp['V'] = "QQW";
        mp['G'] = "EQQ";
        mp['C'] = "WWW";
        mp['X'] = "QWW";
        mp['Z'] = "EWW";
        mp['T'] = "EEE";
        mp['F'] = "EEQ";
        mp['D'] = "EEW";
        mp['B'] = "EQW";
        while (scanf("%s", s + 1) != EOF) {
            f[0].clear(), f[1].clear();
            int n = strlen(s + 1);
            for (int i = 1; i <= n; ++i) {
                int p = i & 1;
                if (i > 1 && s[i] == s[i - 1]) {
                    f[p] = f[p ^ 1];
                    continue;
                }
                f[p].clear();
                string s1 = mp[s[i]];
            //    cout << s1 << endl;
                do {
                    if (i == 1) {
                        f[p][s1] = 3;
                        continue;
                    }
                    f[p][s1] = 1e9; 
                    for (auto &it : f[p ^ 1]) {
                        string s2 = it.first;
                    //    cout << s1 << " " << s2 << endl;
                        int w = it.second;
                        if (s2[1] == s1[0] && s2[2] == s1[1]) {
                            f[p][s1] = min(f[p][s1], w + 1);
                        } else if (s2[2] == s1[0]) {
                            f[p][s1] = min(f[p][s1], w + 2);
                        } else {
                            f[p][s1] = min(f[p][s1], w + 3);
                        }
                    }
                }while (next_permutation(s1.begin(), s1.end()));
            }
            int res = 1e9;
            for (auto &it : f[n & 1]) {
            //    cout << it.first << " " << it.second << endl;
                res = min(res, it.second);
            }
            printf("%d
    ", res + n);
        }
        return 0;
    }
    

    J. MUV LUV EXTRA

    题意:
    给出一个小数,询问小数部分后缀中的(a cdot p - b cdot l)的最大值。
    (a, b)是参数,(p)表示循环节长度,(l)表示后缀长度

    思路:
    将字符串翻转,用(kmp)找循环节即可。

    代码:

    view code
    #include <bits/stdc++.h>
    using namespace std;
    
    typedef long long ll;
    const int N = 1e7 + 10;
    ll a, b;
    char s[N], t[N]; int n;
    void get() {
        int i;
        for (i = 1; s[i]; ++i) {
            if (s[i] == '.') break;
        }
        n = 0;
        for (++i; s[i]; ++i) {
            t[n++] = s[i];
        }
        t[n] = 0;
    }
    struct KMP {
        int Next[N];
        //下标从0开始
        void get_Next(char *s) {
            int len = strlen(s);  
            int i, j;
            j = Next[0] = -1;
            i = 0;
            while (i < len) {
                while (-1 != j && s[i] != s[j]) j = Next[j];
                Next[++i] = ++j;
            }
        }
    }kmp;
    
    int main() {
        while (scanf("%lld%lld", &a, &b) != EOF) {
            scanf("%s", s + 1);
            get();
            reverse(t, t + n); t[n] = 0;
            kmp.get_Next(t);
            ll res = a - b; 
            for (int i = 1; i < n; ++i) {
                ll p = i + 1;
            //    cout << i << " " << kmp.Next[i + 1] << endl;
                ll l = p - kmp.Next[i + 1];
                res = max(res, a * p - b * l);
            }    
            printf("%lld
    ", res);
        }
        return 0;
    }
    
  • 相关阅读:
    使用某些 DOCTYPE 时会导致 document.body.scrollTop 失效
    VB.NET 笔记1
    知识管理系统Data Solution研发日记之一 场景设计与需求列出
    知识管理系统Data Solution研发日记之五 网页下载,转换,导入
    折腾了这么多年的.NET开发,也只学会了这么几招 软件开发不是生活的全部,但是好的生活全靠它了
    分享制作精良的知识管理系统 博客园博客备份程序 Site Rebuild
    知识管理系统Data Solution研发日记之四 片段式数据解决方案
    知识管理系统Data Solution研发日记之二 应用程序系列
    知识管理系统Data Solution研发日记之七 源代码与解决方案
    知识管理系统Data Solution研发日记之三 文档解决方案
  • 原文地址:https://www.cnblogs.com/Dup4/p/11718018.html
Copyright © 2011-2022 走看看