26.7GESP7级

考场

在13:55左右完成了选择和判断

接着开始入手编程题

首先看到T1很明确是一个图上问题,然后有点像树形dp,像之前做的6级的题,想到了DFS、BFS去解

接着看到T2,首先判断要么是一个贪心,要么是线性或区间dp

审题用了5min,然后开始完成T1

T1先观察样例,判断了一下在什么情况下答案的情况,然后想到当有重复遍历的点时\(ans++\),接着又想到如果有多个点(3个及以上)答案会变化很多,但是看到题目保证每个点的度为2时就确定了,然后开始写。因为\(n \le 10^9\),所以就使用了BFS,因为担心栈溢出的RE。写完后过了30min,然后测试样例,发现卡死了,结果是会走回头路,我本来想着不判回头路就是因为用vis数组记录就处理不了我刚刚判定出来的情况,于是转用了一个cnt数组去记录,然后又写了一个vis辅助判断,但没搞清楚优先级,就先跳过了

T2,先模拟了一下样例,却发现贪心每次去最大值居然可以通过样例,而\(n \le 100\),怎么写暴力都ok,于是开写了一个应该是\(O(n^2)\)的贪心暴力,每次先提前处理值,没有嵌套,外层循环是枚举轮数,然后直接每次去处理每个数可以达到的奉献,然后更新,然后发现TLE了,经过检查后发现在一个j的循环当中写了i++,改过来后发现WA,然后感觉T1有点思路了,就转战T1

经过自己造了几张图和特例后发现,答案要么是2,要么是3,然后发下每个图都是环,特殊一点就不是联通的,是单独出来的,发现环的长度为奇数时答案为3,偶数为2,问题就转换为求环的长度。

接着就是一个巨大的错误,我没有直接每一次去查,而是用一个color数组,先初始化为-1,然后第一次用0代表,bfs以1为起点,接着枚举看下有没有-1,有的话就把颜色++,以这个点为起点,继续跑,直到color数组内部没有-1的值就跳出。接着用一个桶去记录每个颜色的数量,有奇数就直接输出3,否则最后输出2。

接着调试了很久,还是走回头路的问题,那么就把queue升级了一下,为queue<pair<int,int>>,然后第一位为前面走的,然后再内部枚举for(int ed : e[u])时加入if(ed == t.first)continue的机制,但样例就是大了一位,然后调,期间又改写成了一个vis[N][N]的类似邻接矩阵去记录的东西,把N改小了,样例能过,但还是WA

后面回去T2,明确是区间dp的思路,但时间只剩下45min了,然后想起石子合并的问题,接着就开始推公式,但到最后面页没有推出来。

考试就这样结束了。

题目

T1

多测,给一张点的度一定为2的无向图,染色,然后一条边的两个端点不能为同一个颜色

\(t \le 100,n \le 10^5,\sum{n} \le 10^5\)

T2

给一个序列,然后每一次删除的操作所给到的价值为左边数+右边数,然后删去本身,使左右两个数相连,如果左边或右边没数,就直接算为0+有数的那一侧的数字,然后求价值最多

\(n \le 100,a[i] \le 10^9\)

我赛后补的代码

T1

#include<bits/stdc++.h>
using namespace std;
const int N = 1e5+10;
vector<int> e[N];
bool vis[N];

int bfs(int s)
{
    queue<int> q;
    q.push(s);
    vis[s] = 1;
    int size = 0;
    while(q.size())
    {
        int u = q.front();
        q.pop();
        size++;
        for(int ed : e[u])
        {
            if(vis[ed]) continue;
            vis[ed] =1;
            q.push(ed);
        }
    }return size;
}

void solve()
{
    int n;
    cin>>n;
    for(int i = 0;i <= n;i ++)
    {
        e[i].clear();
    }
    for(int i = 1;i<=n;i++)
    {
        int u,v;
        cin>>u>>v;
        e[u].push_back(v);
        e[v].push_back(u);
    }
    bool flag = 0;
    for(int i = 1;i<=n;i++)
    {
        if(!vis[i])
        {
            int cnt = bfs(i);
            if(cnt % 2)
            {
                flag = 1;
            }
        }
    }if(flag)
    {
        cout<<3<<'\n';
    }
    else
    {
        cout<<2<<'\n';
    }
}

signed main()
{
    ios::sync_with_stdio(0);cin.tie(0);
    int t;
    cin>>t;
    while(t--)
    {
        solve();
    }
    return 0;
}

T2

#include<bits/stdc++.h>
using namespace std;
#define int long long
const int N = 110;
int dp[N][N];


signed main()
{
    ios::sync_with_stdio(0);
    cin.tie(0);
    int n;
    cin>>n;
    vector<int> a(n+10);
    for(int i = 1;i<=n;i++)
    {
        cin>>a[i];
    }
    for(int len = 1;len<=n;len++)
    {
        for(int l = 1;l + len - 1 <= n;l++)
        {
            int r = l + len - 1;
            dp[l][r] = 0;
            for(int k = l;k <= r;k++)
            {
                int cur = dp[l][k - 1] + dp[k + 1][r] + a[l - 1] + a[r + 1];
                dp[l][r] = max(dp[l][r],cur);
            }
        }
    }
    cout<<dp[1][n];
    return 0;
}
posted @ 2026-09-08 13:22  Zhenggeek  阅读(5)  评论(0)    收藏  举报