8月2日CSP-S赛后总结

8月2日CSP-S模拟赛赛后总结

8 月 2 日  模拟赛  赛后总结 2024 年 8 月 2 日 b y     u h w 177 p o 8月2日 \ \ 模拟赛 \ \ 赛后总结 \\ 2024年8月2日 \\ by \ \ \ uhw177po 82  模拟赛  赛后总结202482by   uhw177po

一、做题情况

  • 第一题比赛 20 p t s 20pts 20pts ,赛后 A C AC AC

  • 第二题比赛 0 p t s 0pts 0pts ,赛后 A C AC AC

  • 第三题比赛 0 p t s 0pts 0pts ,赛后 A C AC AC

  • 第四题比赛 0 p t s 0pts 0pts ,赛后 50 p t s 50pts 50pts

  • 比赛得分 20 / 400   p t s 20/400 \ pts 20/400 pts ,赛后补题 350 / 400   p t s 350 / 400 \ pts 350/400 pts

二、比赛概况

这场模拟赛比较难,T1读了题好久都没有想出解法,想出解法了又被自己给 H a c k Hack Hack 掉了。(实际当时有一种解法是对的)当时就只有 90 min。T2还好,可是贪心没想出(因为当时以为 二分答案,check 死活想不出)T3、T4都读了一遍,发现自己不会做,只好骗分。死得很惨。

三、题解报告

T1:

题面:

做法:

前缀和 板子题,序列可为山峰、递增、递减,然后进行前缀和,轻松做出。

附:AC代码
#include <bits/stdc++.h>
#define int long long
#pragma G++ optimize (2)
#pragma G++ optimize (3)
using namespace std ;
int n , T , a [5000010] , b [5000010] , c [5000010] , x , y ;
signed main () {
    ios::sync_with_stdio (false) ;
    cin.tie (NULL) ; cout.tie (NULL) ;
    freopen ("hot.in" , "r" , stdin) ;
    freopen ("hot.out" , "w" , stdout) ;
    cin >> n >> T ;
    a [n + 1] = 2e9 ; a [0] = -1 ;
    x = 0 ;
    for (int i = 1 ; i <= n ; i ++) {
        cin >> a [i] ;
        if (a [i] > a [i - 1])  x = i ;
        b [i] = x ; 
    }
    for (int i = n ; i >= 1 ; i --) {
        if (a [i] > a [i + 1])  x = i ;
        c [i] = x ;
    }
    while (T --) {
        cin >> x >> y ;
        cout << (c [x] >= b [y] ? "Y\n" : "N\n") ;
    }
    return 0 ;
}

T2:

题面:

做法:

一道 贪心,需要自己推出。

附:AC代码
#include <bits/stdc++.h>
#define int long long
#pragma G++ optimize (2)
#pragma G++ optimize (3)
using namespace std ;
int n , a [100010] , x , p , ans ;
signed main () {
    ios::sync_with_stdio (false) ;
    cin.tie (NULL) ; cout.tie (NULL) ;
    freopen ("divide.in" , "r" , stdin) ;
    freopen ("divide.out" , "w" , stdout) ;
    cin >> n ; // f*ck €€£
    for (int i = 1 ; i <= n ; i ++)  cin >> a [i] ;
    x = a [n] ;
    for (int i = n - 1 ; i >= 1 ; i --)
        if (a [i] > x) {
            p = (a [i] - 1) / x ;
            ans += p ;
            x = a [i] / (p + 1) ;
        }
        else  x = a [i] ; 
    cout << ans ;
    // And more money
    return 0 ;
}

T3:

题面:

做法:

线性dp,可知转移方程式 d p [ i 1 ] = max ⁡ ( d p [ i 1 − 2 ] + max ⁡ ( 0 , a [ i ] [ i 1 − 1 ] + a [ i ] [ i 1 ] ) dp[i1]=\max(dp[i1-2]+\max(0,a[i][i1-1]+a[i][i1]) dp[i1]=max(dp[i12]+max(0,a[i][i11]+a[i][i1]),可以做出。

附:AC代码
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
typedef unsigned int ui;
typedef long double ld;
int n,m,a[1005][1005],dp[1005],ans;
int main(){
	freopen("tunnel.in","r",stdin);
	freopen("tunnel.out","w",stdout);
	scanf("%d%d",&n,&m);
	for(int i=1;i<=n;i++) for(int i1=1;i1<=m;i1++) scanf("%d",&a[i][i1]);
	for(int i=1;i<=n;i++)
	{
		for(int i1=2;i1<=m;i1++) dp[i1]=max(dp[i1-2]+max(0,a[i][i1-1]+a[i][i1]),dp[i1-1]);
		ans+=dp[m];
	}
	dp[1]=0;
	for(int i=1;i<=m;i++)
	{
		for(int i1=2;i1<=n;i1++) dp[i1]=max(dp[i1-2]+max(0,a[i1-1][i]+a[i1][i]),dp[i1-1]);
		ans+=dp[n];
	}
	printf("%d",ans);
    return 0;
}

T4:

题面:

做法:

十分复杂,正解线段树,但不会做。

50 p t s 50 pts 50pts:随便搓一下。

附:AC代码
#include<bits/stdc++.h>
using namespace std;
const int Max_N=2e5;
int n,cnt,a[Max_N+5],pos[Max_N+5],nxt[Max_N+5],R[Max_N+5],rp[Max_N+5];
struct Tree{ int l,r,Mn; } A[Max_N*4+5];
vector<int> p[Max_N+5];
void Build(int x,int l,int r){
	A[x].l=l; A[x].r=r; A[x].Mn=n+1;
	if(l==r) return ;
	Build(x<<1,l,(l+r)>>1);
	Build((x<<1)|1,((l+r)>>1)+1,r);
}
int Ask(int x,int k){
	if(k<=A[x].l&&k<=A[x].Mn) return A[x].r;
	if(A[x].l==A[x].r) return 0;
	if(k<=A[x<<1].r){
		int t=Ask(x<<1,k);
		if(t==A[x<<1].r){
			int w=Ask((x<<1)|1,k);
			if(w) return w;
			else return t;
		} else return t;
	}
	return Ask((x<<1)|1,k);
}
void Add(int x,int p,int w){
	if(A[x].l==A[x].r){
		A[x].Mn=w;
		return;
	}
	if(p<=A[x<<1].r) Add(x<<1,p,w);
	else Add((x<<1)|1,p,w);
	A[x].Mn=min(A[x<<1].Mn,A[(x<<1)|1].Mn); 
}
int main(){
	scanf("%d",&n);
	for(int i=1;i<=n;i++) scanf("%d",&a[i]),p[a[i]].push_back(i),rp[i]=p[a[i]].size();
	for(int i=n;i>=1;i--) pos[i]=n+1;
	for(int i=n;i>=1;i--){
		nxt[i]=pos[a[i]];
		pos[a[i]]=i;
	}
	Build(1,1,n);
	long long ans=n;
	for(int i=n;i>=1;i--){
		if(nxt[i]==n+1||i+1>nxt[i]-1||R[i+1]<nxt[i]-1||a[i+1]!=a[nxt[i]-1]) R[i]=i;
		else {
			int rans=R[nxt[i]];
			rans=min(rans,Ask(1,nxt[i]));
			if(rans==0) R[i]=nxt[i],++ans;
			else {
				int x=upper_bound(p[a[i]].begin(),p[a[i]].end(),rans)-p[a[i]].begin();
				R[i]=p[a[i]][x-1]; ans+=x-rp[i];
			}
		}
		if(nxt[i]<=n) Add(1,nxt[i],i);
	}
	printf("%lld\n",ans);
	return 0;
} 

四、赛后总结

死得太惨了。(fuck €€£

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值