SMU Summer 2023 Contest Round 1

SMU Summer 2023 Contest Round 1

A. The Contest

\(m\)\(0\) 和 完成时间大于最后一个时刻时,说明都无法在规定条件内完成,输出\(-1\).

将时间段拆开放一个数组循环, 找到第一个大于等于完成时间的位置,若此时\(i\) 为奇数, 说明该完成时间处在一个工作时间段内,输出\(sum\)即可, 否则就是处于非工作时间,这时就要输出下一个工作时间段的开始时刻.

#include<bits/stdc++.h>
#define endl '\n'
#define int long long

using namespace std;

int n,m,t,k;
void solve(){
    cin >> n;
    vector<int> a(n);
    int sum = 0;
    for(auto &i : a){
        cin >> i;
        sum += i;
    }
    cin >> m;
    if(!m){
        cout << -1 << endl;
        return ;
    }
    vector<int> time;
    for(int i = 0;i < m;i ++){
        cin >> t >> k;
        time.push_back(t);
        time.push_back(k);
    }
    if(sum > time.back()){
        cout << -1 << endl;
        return ;
    }else {
        for(int i = 0;i < time.size();i ++){
            if(time[i] >= sum){
                if(i & 1){
                    cout << sum << endl;
                    break;
                }else{
                    cout << time[i] << endl;
                    break;
                }
            }
        }
    }
}
signed main()
{
    ios::sync_with_stdio(false);
    cin.tie(nullptr);cout.tie(nullptr);
    int Ke_scholar = 1;
//    cin >> Ke_scholar;
    while(Ke_scholar--)
        solve();
    return 0;
}

B. The Golden Age

暴力将区间内的不吉利数算出后排序,更新区间最大值即可.(注意精度问题)

#include<bits/stdc++.h>
#define endl '\n'
#define int long long
#define  inf 0x3f3f3f3f

using namespace std;

int n,m,t,k;
void solve(){
    int x,y,l,r;
    cin >> x >> y >> l >> r;
    vector<int> ans;
    for(int i = 1; i != 0; i = i * (i > r / x ? 0 : x))//当值超过r时就不取,防止爆精度
        for(int j = 1;j != 0; j = j * (j > r / y ? 0 : y))
            if(i + j >= l && i + j <= r)
                ans.push_back(i + j);
    int res = 0;
    if(ans.size()) {
        int L = l - 1;
        sort(ans.begin(), ans.end());
        for(int i = 0; i < ans.size();i ++){
            res = max(res, ans[i] - L - 1);
            L = ans[i];
        }
        if (ans.front() != l)
            res = max(ans.front() - l, res);
        if (ans.back() != r) {
            res = max(r - ans.back(), res);
        }
    }else{
        res = r - l + 1;
    }
    cout << res << endl;
}
signed main()
{
    ios::sync_with_stdio(false);
    cin.tie(nullptr);cout.tie(nullptr);
    int Ke_scholar = 1;
//    cin >> Ke_scholar;
    while(Ke_scholar--)
        solve();
    return 0;
}

C. The Tag Games

要使得行动步数最长,则\(B\)就要找到一条\(A\)\(B\)路径上的最长链, 因此我们可以先建一个图, 对每个点找到它当前点向后延伸的最长链长度,然后用path数组去记录\(A\)\(B\)的这条路径,在这条路径上找到\(A\)能到达最长链的最大值

\(i\) 就是A行动的步长.

\(deep[path[i]] - deep[path[j]]\) 就是\(A\)\(B\) 之间的距离.

\(dis[path[i]] - 1\)就是\(B\)当前所在点距离最长链的长度.

因为更新的这个值是\(A\)到达最长链的长度,且\(A\)\(B\)的步数是同步的,所以最后需要\(×2​\)

#include<bits/stdc++.h>
#define endl '\n'
#define int long long
#define  inf 0x3f3f3f3f

using namespace std;

const int N = 2e5 + 10, mod = 1e18;
typedef pair<int,int> PII;
int n,m,t,k;
void solve(){
    cin >> n >> m;
    vector<int> g[n + 1];
    for(int i = 0;i < n - 1;i ++){
        int x,y;
        cin >>x >> y;
        g[x].push_back(y);
        g[y].push_back(x);
    }
    vector<int> pre(n + 1),deep(n + 1),dis(n + 1),path(n + 1);
    
    function<int(int,int,int)> dfs = [&](int u,int v, int d){
        int len = 0;
        pre[u] = v;
        deep[u] = d;
        for(auto i : g[u]){
            if(i == pre[u])
                continue;
            len = max(len, dfs(i,u,d + 1));
        }
        return dis[u] = len + 1;
    };
    dfs(1, -1, 0);

    t = m;
    int cnt = 0;
    while(t != - 1){
        path[cnt++] = t;
        t = pre[t];
    }
    int ans = 0;
    for(int i = 0, j = cnt - 1;i < j; j --, i ++){
        ans = max(ans, (i + deep[path[i]] - deep[path[j]] + dis[path[i]] - 1) * 2);
    }

    cout << ans << endl;
}
signed main()
{
    ios::sync_with_stdio(false);
    cin.tie(nullptr);cout.tie(nullptr);
    int Ke_scholar = 1;
//    cin >> Ke_scholar;
    while(Ke_scholar--)
        solve();
    return 0;
}
posted @ 2023-07-11 04:05  Ke_scholar  阅读(3)  评论(0编辑  收藏  举报