首页 > 其他分享 >Toyota Programming Contest 2024#7(AtCoder Beginner Contest 362)

Toyota Programming Contest 2024#7(AtCoder Beginner Contest 362)

时间:2024-07-14 23:29:27浏览次数:12  
标签:AtCoder y2 Beginner Contest int maxn Y1 include dis

⚪题和板题大赛/jk

好像能切的样子,但是太菜了,唐了 8 罚。

A - Buy a Pen

输出除去某个颜色以外,其他颜色代表的最大值。

点击查看代码
#include<bits/stdc++.h>
using namespace std;
int a,b,c;
string s;
signed main(){
    cin>>a>>b>>c;
    cin>>s;
    if(s[0]=='R') a=1033;
    else if(s[0]=='G') b=1033;
    else c=1033;
    cout<<min(a,min(b,c));
    return 0;
}

Right Triangle

给出三个点的坐标,判断该△是不是Rt。

勾股定理。Y1,又踩一次坑。

点击查看代码
#include<bits/stdc++.h>
using namespace std;
int x1,x2,x3,Y1,y2,y3;
int a[100];
int dis(int x1,int Y1,int x2,int y2){
    return (x1-x2)*(x1-x2)+(Y1-y2)*(Y1-y2);
}
signed main(){
    cin>>x1>>Y1>>x2>>y2>>x3>>y3;
    a[0]=dis(x1,Y1,x2,y2),a[1]=dis(x1,Y1,x3,y3),a[2]=dis(x2,y2,x3,y3);
    // sort(a,a+2);
    if(a[0]+a[1]==a[2]||a[1]+a[2]==a[0]||a[2]+a[0]==a[1]) cout<<"Yes";
    else cout<<"No";
    return 0;
}

Sum = 0

数列 \(a\) 满足 \(a_i\in[L_i,R_i]\),构造一组 \(a\),使得 \(\sum a_i=0\),或报告无解。

考虑贪心,若 \(l=\sum L_i>0\) 或 \(r=\sum R_i<0\) 显然无解。

否则继续操作,贪心地向 \(0\) 靠近:

  • 若 \(r\ge R_i-L_i\),显然即使将 \(a_i\) 设为 \(L_i\),\(r\) 也大于等于 \(0\),一定是不劣的。
  • 否则,将 \(a_i\) 设为 \(R_i-r\) 即可将当前序列和变成 \(\sum\limits_{i+1\sim r}R_i\),以后的 \(a_i\) 全为 \(R_i\) 即可。
点击查看代码
#include<bits/stdc++.h>
#define int long long
using namespace std;
const int maxn=2e5+3;
int n,l[maxn],r[maxn],sl,sr;
signed main(){
    cin>>n;
    for(int i=1;i<=n;i++){
        cin>>l[i]>>r[i];
        sl+=l[i],sr+=r[i];
    }
    if(sl>0||sr<0){
        cout<<"No";
        return 0;
    }
    cout<<"Yes\n";
    for(int i=1;i<=n;i++){
        if(sr==0){ cout<<r[i]<<' ';}
        else if(sr-(r[i]-l[i])>=0){
            cout<<l[i]<<' ';
            sr-=(r[i]-l[i]);
        }else{
            cout<<r[i]-sr<<' '; sr=0;
        }
    }
    return 0;
}

Shortest Path 3

给你简单无向图,点有点权,边有边权,求 \(1\) 为源点的最短路。

板子。松弛的时候把点权加进去就行了。

点击查看代码
#include<iostream>
#include<vector>
#include<queue>
using namespace std;
#define int long long
const int maxn=6e5+3;
const int maxm=4e5+3;
const int inf =0x3f3f3f3f3f3f3f3f;
struct edge{
	int v,w;
	edge(int v=0,int w=0): v(v),w(w){}
};
vector<edge>e[maxn];
#define pb emplace_back
int n,m,s,a[maxn],vis[maxn];
struct di{
	int id,dis;
	di(int id=0,int dis=0): id(id),dis(dis){}
	bool operator<(const di o)const{return dis>o.dis;}
};
priority_queue<di>q;
int dis[maxn];
void dijkstra(){
	for(int i=1;i<=m+n*2;i++)
		dis[i]=inf;
	q.push(di(s,dis[s]=a[s]));
	while(!q.empty()){
		di u=q.top();
		q.pop();
		if(!vis[u.id]){
            vis[u.id]=1;
			for(edge v:e[u.id]){
				if(dis[v.v]>dis[u.id]+v.w+a[v.v]){
					q.push(di(v.v,dis[v.v]=dis[u.id]+v.w+a[v.v]));
				}
			}
		}
	}
	for(int i=2;i<=n;i++){
		cout<<dis[i]<<' ';
	}
}
signed main(){
	cin>>n>>m;s=1;
    for(int i=1;i<=n;i++) cin>>a[i];
	for(int i=1,u,v,w;i<=m;i++){
		cin>>u>>v>>w;
		e[u].pb(edge(v,w));
		e[v].pb(edge(u,w));
	}
	dijkstra();
	return 0;
}

Count Arithmetic Subsequences

给你一个数列 \(a\),对于 \(\forall i\in[1,n]\) 求长度为 \(i\) 的等差子序列个数。

\(n\le 80,a_i\le 10^9\)

虚空写 DP 传奇(

DP 比较明显,设 \(f_{d,i,k}\) 表示公差为 \(d\),以 \(i\) 为结尾的,长度为 \(k\) 的等差数列数量,则有转移:

\[f_{d,i,k}=\sum\limits_{j=1}^{i-1}[a_i-a_j=d]f_{d,j,k-1} \]

如果每次清空数组,就可以把 \(d\) 一维消去。在枚举过程中累加答案。但是枚举 \(d\) 的时间复杂度巨大,不可通过。

真的吗?

由于 \(n\le 80\),则差的数量上界为 \(\frac{n(n-1)}{2}<320\),所以我们可以把差存起来,直接从里面枚举,而不是枚举值域,最后时间复杂度 \(O(n^4)\)。

点击查看代码
#include<bits/stdc++.h>
#define int long long
using namespace std;
const int mod=998244353;
int n,a[888],b[888],del[88888],tot,f[888][888],g[888];
int ggg[87888],top;
signed main(){
    cin>>n;
    for(int i=1;i<=n;i++) cin>>a[i];
    for(int i=1;i<=n;i++){
        for(int j=1;j<=n;j++){
            ggg[++top]=a[i]-a[j];
        }
    }
    sort(ggg+1,ggg+top+1);
    int tot=unique(ggg+1,ggg+top+1)-ggg-1;
        for(int i=1;i<=n;i++) f[i][1]=1;
    for(int div=1;div<=tot;div++){
        for(int i=1;i<=n;i++){
        for(int k=2;k<=i;k++)
            for(int j=1;j<i;j++){
                if(a[i]-a[j]==ggg[div])
                    f[i][k]=(f[i][k]+f[j][k-1])%mod;
            }
        }
        for(int i=1;i<=n;i++)
        for(int k=2;k<=i;k++){
            g[k]=(g[k]+f[i][k])%mod;
            f[i][k]=0;
        }
    }
    cout<<n<<' ';
    for(int i=2;i<=n;i++) cout<<g[i]<<' ';
    return 0;
}

Perfect Matching on a Tree

给你一棵树,构造方案两两匹配点使得所有匹配点的距离和最大。

看懂了,大概是树形 DP 找重心,以重心为根,然后构造的话就在不同子树内找点连边即得最大,贪心是对的。

时间复杂度 \(O(n)\),有个技巧是先把同一子树内的点排在一起,考虑到重心的性质,每个子树大小不超过 \(\left\lfloor\frac{n}{2}\right\rfloor\),所以将 \(i\) 和 \(i+\left\lfloor\frac{n}{2}\right\rfloor\) 匹配,就能保证这两点不在同一子树内。

代码待补。

Count Substring Query

AC 自动机板题,甚至只要改输入(

绷不住了

点击查看代码
#include<bits/stdc++.h>
using namespace std;
const int maxn=5e5+3;
const int maxs=5e5+3;
int n,node,cnt;
char s[maxs],t[maxs];
int trie[maxn][30];
int fail[maxs],word[maxn],sum[maxs],in[maxs];
void insert(){
	int u=0;
	for(int i=0;s[i];i++){
		if(!trie[u][s[i]-'a'])
			trie[u][s[i]-'a']=++node;
		u=trie[u][s[i]-'a'];
	}
	word[++cnt]=u;
}
queue<int>q;
void Fail(){
	for(int i=0;i<26;i++) if(trie[0][i]) q.push(trie[0][i]);
	while(!q.empty()){
		int u=q.front();
		q.pop();
		for(int i=0;i<26;i++){
			if(trie[u][i]) 
				q.push(trie[u][i]),fail[trie[u][i]]=trie[fail[u]][i];
			else trie[u][i]=trie[fail[u]][i];
		}
	}
	for(int i=0;i<=node;i++) in[fail[i]]++;
}
void query(){
	int u=0;
	for(int i=0;t[i];i++){
		u=trie[u][t[i]-'a'];
		sum[u]++;
	}
}
void topo(){
	for(int i=0;i<=node;i++) if(!in[i]) q.push(i);
	while(!q.empty()){
		int u=q.front();
		q.pop();
		sum[fail[u]]+=sum[u];
		if(!--in[fail[u]])
			q.push(fail[u]);
	}
}
signed main(){
	cin>>t; cin>>n;
	for(int i=0;i<n;i++) cin>>s, insert();
	Fail();  query(); topo();
	for(int i=1;i<=n;i++) cout<<sum[word[i]]<<'\n';
	return 0;
} 

标签:AtCoder,y2,Beginner,Contest,int,maxn,Y1,include,dis
From: https://www.cnblogs.com/DEV3937/p/18302210/abc362

相关文章

  • Solution - Atcoder AGC022D Shopping
    考虑到不管怎么走,都是\(0\)最后又绕回\(0\),于是答案肯定是\(2L\)的倍数。那么考虑\(\frac{\operatorname{ans}}{2L}\)即可。那么对于\(t_i\),可以先让答案加上\(\lfloor\frac{t_i}{2L}\rfloor\),同时令\(t_i\leftarrowt_i\bmod2L\)。原因就是考虑到这被去除掉的\(2......
  • SMU Summer 2024 Contest Round 2 (7.9)zhaosang
    A-Ahttp://162.14.124.219/contest/1006/problem/A考查用vector画图我枚举到n==5才开始用,浪费40分钟,还是找规律太慢,得多学做题代码如下:一坨#include<bits/stdc++.h>usingnamespacestd;usingll=longlong;constllN=1e6+8;charv[1000001];intw[10000001];ll......
  • SMU Summer 2024 Contest Round 3(7.10)zhaosang
    打的最菜一次,最惨一次,题读假了A-Ahttp://162.14.124.219/contest/1007/problem/A签到题要解决这道题,素数对,数据量不是很大,所以我们可以先预处理素数,这个偶数肯定是等于小于它的两个素数,所以只需要遍历到小于它即可,把素数存起来,然后这两个素数的和等于这个偶数,并且要求相差最小......
  • 2023 Henan Provincial Collegiate Programming Contest
    和零时加的队友打了一下,计算几何摆了,最优化摆了,adhoc摆了。A.小水獭游河南枚举前缀,是\(O(|\Sigma|)\)的,然后判断一下是不是回文串即可。B.ArtforRest昨天才做过这个套路的加强版。显然只用判断类似\(\max(a,b)<\min(b+1,c)\)的条件。暴力枚举是调和级数的。C.Toxel......
  • Toyota Programming Contest 2024#7(AtCoder Beginner Contest 362)
    这场比赛还是比较水的A,B,C跳过D题dij把点权和边权都转换为边权即可E题DP可以用\(map\)存一下等差数列的差先说\(O(n^4)\),\(f_{len,i,j,t}\)分别表示长度,现在在\(i\),上一个在\(j\)显然动态转移方程就有了\(f_{len,i,j,k}=\sum_{k=1}^{k=j-1}f_{len-1,j,k,t}\)点击查看......
  • AtCoder Beginner Contest 362 补题记录(A~E,G)
    A分三类情况讨论即可。voidsolveqwq(){intr=io.read(),g=io.read(),b=io.read();stringqwq=io.readstring();if(qwq=="Blue")printf("%lld\n",min(r,g));elseif(qwq=="Red")printf("%lld\n",......
  • Solution - Atcoder AGC021D Reversed LCS
    考虑到\(\operatorname{LCS}(T,T')\)这个形式实在是不太优美,考虑转化一下形式。感受一下,能够知道\(T\)的最长回文子序列\(|\operatorname{LPS}(T)|=|\operatorname{LCS}(T,T')|\)。具体证明可以见zhihu,本人暂时还没看懂。那么接下来对于单个串的\(\operatorname{LPS......
  • Solution - Atcoder ARC127E Priority Queue
    考虑转化一下,每个最后留下来的集合都相对的对应着一个被删除的集合。于是考虑去对被删除的数去计数。然后贪心的,去让每一次\(2\)操作删除的数都是前面加入中还剩下的最后加入的数(因为有的可能被前面的\(2\)操作删了)。对于证明,考虑到如果不是剩下的最后加入的,那么中间可能会......
  • SMU Summer 2024 Contest Round 3
    1.To3原题链接:http://162.14.124.219/contest/1007/problem/I记录数组中除3余数的种类和个数,以及数组元素总和除3的余数,最后判断(考虑总余数为1,两个元素余数为2和总余数为2,两个元素余数为1的特殊情况)查看代码#include<bits/stdc++.h>#defineintlonglongusingnamespa......
  • SMU Summer 2024 Contest Round 2
    1.MinimumWidth原题链接:http://162.14.124.219/contest/1006/problem/C二分一行最大容量,如果check小于等于总行数就扩大,反之则缩小查看代码#include<bits/stdc++.h>#defineintlonglongusingnamespacestd;intn,m;inta[1000000],b[1000000];boolcheck(intx){......