2024.5.28晚训题解

news2024/12/23 22:16:13

提前预告,市赛初中组会考算法题,应该会有两道模板题
比如DFS BFS 二分 简单动态规划,虽然我们没学多久,但是模板题你还是要会写的

A题 编辑距离 动态规划
注意多组输入

#include<iostream>
using namespace std;
int dp[1005][1005];
//dp[i][j]把s字符串的前i个经过一系列操作变成b字符串的前j个的最小代价 
char s[1005];
char b[1005];
int main(){
	int n,m;
	while(scanf("%d%s%d%s",&n,s+1,&m,b+1)!=EOF){
		for(int i=0;i<=m;i++){
			dp[0][i]=i; //插入 
		}
		for(int i=0;i<=n;i++){
			dp[i][0]=i; //删除 
		}
		for(int i=1;i<=n;i++){
			for(int j=1;j<=m;j++){
				if(s[i]==b[j])dp[i][j]=dp[i-1][j-1];//此时i j位置相同,可以直接从s[i-1]->b[j-1] 转移过来
				else{
					dp[i][j]=min(dp[i-1][j-1]+1,min(dp[i-1][j]+1,dp[i][j-1]+1));
					/*
					dp[i-1][j]+1 表示我们把s[1~i] 删掉i位置,得到s[1~i-1]  从它变到b[1~j]  
						dp[i][j-1]+1 表示我们把s[1~i]  从它变到b[1~j-1]  然后插入一个b[j] 
							dp[i-1][j-1]+1    从s[1~i-1]  从它变到b[1~j-1]   对于s[i] 直接修改为b[j]   
					*/
				} 
			}
		}
		printf("%d\n",dp[n][m]);
	}
	return 0;
}

B题 最长上升子序列 (N^2)版本

#include<iostream>
using namespace std;
int A[1005];
int dp[1005]; //dp[i]表示以A[i]结尾的最长上升子序列元素 
int main(){
    int n;
    scanf("%d",&n);
    int ans=1;
    for(int i=1;i<=n;i++){
    	dp[i]=1;
		scanf("%d",&A[i]);
    	for(int j=i-1;j>=1;j--){
    		if(A[j]<A[i]){
    			dp[i]=max(dp[i],dp[j]+1);
			}
		}//考虑拼接的方法,想寻得dp[i],往前面找,跟某个元素拼接起来  形成以A[i]
		//结尾的上升子序列,那么所有的子序列取max也就是最大的   
		ans=max(ans,dp[i]);//但是答案不一定是以A[n]结尾  
	}
	printf("%d",ans);
	return 0;
}

当然,其实还有优化写法,利用二分,即可实现NlogN 的时间复杂度
我建议还是背一下(理解一下)
代码不是完全的,请看看思路

ll dp[N];
ll a[N];
ll b[N];
signed  main() {
	ll n;
	read(n);
	for(int i=1; i<=n; i++) {
		read(a[i]);
	}
	ll cnt=0;
	for(int i=1; i<=n; i++) {
		if(cnt==0||a[i]>dp[cnt]) {
			dp[++cnt]=a[i];//首位置要放入元素
			//如果当前元素A【i】比当前序列结尾的还要大,放进来  上升 
			continue;
		} else {
		    //如果当前元素A[i]≤ 序列结尾  
		    //考虑查找序列里面合适的值,替换掉 
		    //举例  1 100 2   
		    //实际上用2替换100会更优,因为你过程的元素越大,越不利于后续上升
			dp[upper_bound(dp+1,dp+1+cnt,a[i])-dp]=a[i];
		}
	}
	printf("%lld",cnt);
}

右边的数字即全球通过人数
在这里插入图片描述

C题题解
我觉得这是不能错的题。 1 ∗ 1 1*1 11的格子不用说了,啥地方都能放
主要看 2 ∗ 2 2*2 22的,一个板只能放最多两个 2 ∗ 2 2*2 22
所以你要先计算出放 b b b 2 ∗ 2 2*2 22的要多少板 ,以及这些板还有多少个格子没放的。
如果多余没放的格子足够放完 a a a 1 ∗ 1 1*1 11的 ,那么答案就是 2 ∗ 2 2*2 22需要的板子数
否则你还需要用(a-多余格子) 这么多个格子去计算还需要多少块板

#include<bits/stdc++.h>
using namespace std;
int main(){
	int t;
	scanf("%d",&t);
	while(t--){
	int a,b;	
	scanf("%d%d",&a,&b);	
	int le=0;
	if(b%2==0)le=(15-8)*(b/2);
	if(b%2){
		le=(15-8)*(b/2)+15-4;
	}
	int ans=b/2+b%2;
	if(a<=le)printf("%d\n",ans);
	else{
	 	printf("%d\n",ans+(a-le)/15+((a-le)%15!=0));	
	}
	}
	return 0;
}

D题题解
这其实就是个简单的模拟题,你把输入的字符串字母sort一遍,把密码表处理出来
然后枚举字符串开始翻译就行了

#include<bits/stdc++.h>
using namespace std;
char s[200005];
char b[30];
bool vis[30];
char sw[30];
int main(){
	int t;
	scanf("%d",&t);
	while(t--){
		memset(vis,false,sizeof(vis));
		int n;
		scanf("%d",&n);
		scanf("%s",s+1);
		int len=0;
		for(int i=1;i<=n;i++){
			if(vis[s[i]-'a'])continue;
			else{
				vis[s[i]-'a']=true;
				b[++len]=s[i];
			}
		}
		sort(b+1,b+1+len);
		for(int i=1;i<=len/2+1;i++){
			sw[b[i]-'a']=b[len-i+1];
			sw[b[len-i+1]-'a']=b[i];
		}
		for(int i=1;i<=n;i++){
			s[i]=sw[s[i]-'a'];
		}
		printf("%s\n",s+1);
	}
	return 0;
}

E题题解
这个标记题需要一定数理知识
对于一个三元组 A [ i − 2 ] , A [ i − 1 ] , A [ i ] {A[i-2],A[i-1],A[i]} A[i2],A[i1],A[i] 我们得标记它们,你可以想象一下,什么样的三元组能相互之间算答案?有两个元素一样对不对,我们直接把一样的元素标记起来,记为一个二元组。

以此标记该三元组里面的二元组,按顺序标记
每次计算答案的时候,查找一下当前三元组前面,有多少个跟自己的二元组一样的三元组,该操作不保证过滤了重复元素
因此我们需要查询该三元组前面有多少个跟自己一模一样的三元组,因为一模一样是不会产生答案的,所以要减去3倍

#include<bits/stdc++.h>
using namespace std;
int A[200005];
map<pair<int,int>,int >vis_1;
map<pair<int,int>,int >vis_2;
map<pair<int,int>,int >vis_3;
map<pair<pair<int,int>,int> ,int >pre;
int main(){
	int t;
	scanf("%d",&t);
	while(t--){
		int n;
		scanf("%d",&n);
		long long int ans=0;
		for(int i=1;i<=n;i++){
			scanf("%d",&A[i]);
			if(i>=3){
			//    当前三元组A[i-2] A[i-1] A[i] 
			  //  三种可能: A[i-2]A[i]相等   A[i-1]A[i]相等   A[i-2]A[i-1]相等  这三个二元组可以作为标记去查询
			    
				ans=ans+vis_1[make_pair(A[i-2],A[i-1])];
				//统计前面有多少个跟A[i-2] A[i-1]值一样的二元组(先不考虑前面存在跟自己完全一样的三元组,那么答案就是加这个二元组标记的个数,视作前面出现的该二元组的元素与当前A[i]都不一样)
				//A[i-2] A[i-1]   ?        前面的一些三元组结构
				//A[i-2] A[i-1] A[i]       当前三元组    
				ans=ans+vis_2[make_pair(A[i-2],A[i])];
				ans=ans+vis_3[make_pair(A[i-1],A[i])];	
				vis_1[make_pair(A[i-2],A[i-1])]++;
				vis_2[make_pair(A[i-2],A[i])]++;
				vis_3[make_pair(A[i-1],A[i])]++;
				ans=ans-3*pre[make_pair(make_pair(A[i-2],A[i-1]),A[i])];
				//考虑存在重复的问题,举例
				//如果前面有x个三元组满足值与当前三元组(A[i-2],A[i-1],A[i])一样,那么我们就多计算了x个答案,因为完全相等的三元组不产生答案贡献,枚举了三个二元组,所以减法要减去*3  
				pre[make_pair(make_pair(A[i-2],A[i-1]),A[i])]++;
			}
		}
		printf("%lld\n",ans);
		vis_1.clear();
		vis_2.clear();
		vis_3.clear();
		pre.clear();
	}
	return 0;
}

F题题解
考虑东西南北指令,划分为两部分
一个部分是: 北南凑一对,相当于抵消移动 东西凑一对,相当于抵消移动

第一部分完成后,未凑对的剩下来的只能是北/南里面的一种,剩下的我们要考虑能不能均分给两个人,同理东西

计算北南的对数,东西的对数
北南可以按A人先的顺序轮流分配
东西可以按B人先的顺序轮流分配
接下来分配剩余的未配对的,注意如果剩余奇数个,肯定不能保证最终两个人走在同一个地方

#include<bits/stdc++.h>
using namespace std;
char s[200005];
int vis[30];
int A[30];
int B[30];
int main(){
	int t;
	scanf("%d",&t);
	int N,S,E,W;
	N='N'-'A';
	S='S'-'A';
	E='E'-'A';
	W='W'-'A';
	while(t--){
		int n;
		scanf("%d",&n);
		scanf("%s",s+1);
		vis[N]=vis[S]=vis[E]=vis[W]=0;
		A[N]=A[S]=A[E]=A[W]=0;
		B[N]=B[S]=B[E]=B[W]=0;
		for(int i=1;i<=n;i++){
			vis[s[i]-'A']++;
		}
		int ns=min(vis[N],vis[S]);
		int ew=min(vis[E],vis[W]);//配对相消  
		int lens=max(vis[N],vis[S])-min(vis[N],vis[S]);
		int leew=max(vis[E],vis[W])-min(vis[E],vis[W]); 
		for(int i=1;i<=ns;i++){
			if(i%2){
				A[N]++;
				A[S]++;
			}
			else{
				B[N]++;
				B[S]++;
			}
		}
		for(int i=1;i<=ew;i++){
			if(i%2){
				B[E]++;
				B[W]++;
			}
			else{
				A[E]++;
				A[W]++;
			}
		}
		//双消+偶数
		//单消 + 偶 
		if(lens%2||leew%2){
			printf("NO\n");
			
		}
		else{
			int op;
			if(vis[N]>vis[S])op=N;
			else op=S;
			A[op]+=lens/2;
			B[op]+=lens/2;
			if(vis[E]>vis[W])op=E;
			else op=W;
			A[op]+=leew/2;
			B[op]+=leew/2;
			if((A[N]+A[S]+A[E]+A[W])==0||(B[N]+B[S]+B[E]+B[W])==0){
				printf("NO\n");continue;
			}	
			for(int i=1;i<=n;i++){
				if(A[s[i]-'A']){
					A[s[i]-'A']--;
					printf("R");
				}
				else{
					B[s[i]-'A']--;
					printf("H");
				}
			}
			printf("\n");
		}
	}
	return 0;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1709891.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

unity3D获取某天的0点和23点59分59秒

系列文章目录 unity工具 文章目录 系列文章目录unity工具 &#x1f449;一、前言&#x1f449;二、获取某一天的0点和23点59分59秒1-1.代码如下1-2.调用方法如下1-2-1.获取当天的时间1-2-2.获取某一天的时间 &#x1f449;三、当月第一天0时0分0秒&#x1f449;四、当月最后一…

SHELL编程(三)网络基础命令 Makefile

目标 一、网络基础及相关命令&#xff08;一&#xff09;网络相关命令&#xff08;二&#xff09;重启网络服务 二、Makefile&#xff08;一&#xff09;标签式语法&#xff08;二&#xff09;目标:依赖 式语法1. 格式2. 编译流程&#xff1a;预处理 编译 汇编 链接3. 目标和伪…

TiDB-从0到1-体系结构

TiDB从0到1系列 TiDB-从0到1-体系结构TiDB-从0到1-分布式存储TiDB-从0到1-分布式事务 一、TiDB体系结构图 TiDB基础的体系架构中有4大组件 TiDB Server&#xff1a;用于处理客户端的请求PD&#xff1a;体系的大脑&#xff0c;存储元数据信息TiKV&#xff1a;存储数据TiFlash…

Stable Diffusion 模型演进:LDM、SD 1.0, 1.5, 2.0、SDXL、SDXL-Turbo 等

节前&#xff0c;我们星球组织了一场算法岗技术&面试讨论会&#xff0c;邀请了一些互联网大厂朋友、参加社招和校招面试的同学。 针对算法岗技术趋势、大模型落地项目经验分享、新手如何入门算法岗、该如何准备、面试常考点分享等热门话题进行了深入的讨论。 合集&#x…

Vue3+Ant design 实现Select下拉框一键全选/清空

最近在做后台管理系统项目的时候&#xff0c;产品增加了一个让人非常苦恼的需求&#xff0c;让在Select选择器中添加一键全选和清空的功能&#xff0c;刚开始听到的时候真是很懵&#xff0c;他又不让在外部增加按钮&#xff0c;其实如果说在外部增加按钮实现全选或者清空的话&a…

触摸屏是输入设备还是输出设备?

从功能上讲&#xff0c;触摸屏理应属于输入设备&#xff0c;之所以有很多用户会误会它是输出设备&#xff0c;是因为将其与“触摸显示屏”搞混了&#xff0c;以手机屏幕为例&#xff0c;它并不是单层屏幕&#xff0c;而是有多个不同功能和作用组成的集成屏&#xff0c;这类带有…

ubuntu-24.04系统静态Mac和IP配置

操作系统版本&#xff08;桌面版&#xff09;&#xff1a;ubuntu-24.04-desktop-amd64.iso 原因说明&#xff1a;因网络的IP地址和Mac是预分配的&#xff0c;所以ubuntu系统需要修改网卡的mac地址和IP才能访问&#xff0c;网络查了半天资料都没成功&#xff0c;后再界面提示&a…

【Python】 Python中的“命名元组”:简单而强大的数据结构

基本原理 在Python中&#xff0c;namedtuple是tuple的一个子类&#xff0c;它允许我们为元组的每个位置指定一个名字。这种数据结构非常适合用于需要固定字段和值的场景&#xff0c;例如数据库查询的结果或配置文件中的设置。 namedtuple提供了一种方便的方式来访问元组中的元…

力扣2028. 找出缺失的观测数据

题目&#xff1a; 现有一份 n m 次投掷单个 六面 骰子的观测数据&#xff0c;骰子的每个面从 1 到 6 编号。观测数据中缺失了 n 份&#xff0c;你手上只拿到剩余 m 次投掷的数据。幸好你有之前计算过的这 n m 次投掷数据的 平均值 。 给你一个长度为 m 的整数数组 rolls &a…

防止浏览器缓存了静态的配置等文件(例如外部的config.js 等文件)

防止浏览器缓存了静态的配置文件 前言1、在script引入的时候添加随机数1.1、引入js文件1.2、引入css文件2、通过html文件的<meta>设置防止缓存3、使用HTTP响应头:前言 在实际开发中浏览器的缓存问题一直是一个很让人头疼的问题,尤其是我们打包时候防止的静态配置文件c…

在 PhpStorm 中自定义代码片段

在 PhpStorm 中自定义代码片段的步骤如下: 打开 PhpStorm,进入 “File” > “Settings” > “Editor” > “Live Templates”。 在右侧面板中,点击 “” 号,选择 “Live Template”。 在弹出的窗口中: Abbreviation: 输入您想要自动补全的缩写,比如 “de”Template …

【强训笔记】day24

NO.1 思路&#xff1a;递归。 代码实现&#xff1a; class Solution { public:bool IsBalanced_Solution(TreeNode* pRoot) {return dfs(pRoot)!-1;}int dfs(TreeNode* root){if(rootnullptr) return 0;int leftdfs(root->left);if(left-1) return -1;int rightdfs(root-…

深度揭秘:蓝海创意云渲染农场的五大特色功能

在当今数字化时代&#xff0c;影视制作、效果图设计等领域对于高质量的渲染需求日益增长。在这个背景下&#xff0c;云渲染平台成为了行业中不可或缺的一部分&#xff0c;它为用户提供了高效、灵活的渲染解决方案。蓝海创意云渲染农场https://www.vsochina.com/cn/render蓝海创…

WWW24因果论文(1/8) | 利用强化学习(智能体)进行因果问答

【摘要】因果问题询问不同事件或现象之间的因果关系。它们对于各种用例都很重要&#xff0c;包括虚拟助手和搜索引擎。然而&#xff0c;许多当前的因果问答方法无法为其答案提供解释或证据。因此&#xff0c;在本文中&#xff0c;我们旨在使用因果关系图来回答因果问题&#xf…

昂科烧录器支持Infineon英飞凌的磁性位置传感器TLE4998S8D

芯片烧录行业领导者-昂科技术近日发布最新的烧录软件更新及新增支持的芯片型号列表&#xff0c;其中Infineon英飞凌的磁性位置传感器TLE4998S8D已经被昂科的通用烧录平台AP8000所支持。 TLE4998S8D是一款磁性位置传感器&#xff0c;经过专门设计&#xff0c;满足高精度角度和位…

实施阶段(2024年5月)

【项目活动1】斐波拉契数列第n项的值&#xff1f; 数学思想&#xff1a;第一项和第二项的值都为1&#xff0c;从第三项开始值为前两项的和。 方法一&#xff1a;迭代 迭代变量&#xff1a;f1和f2 迭代表达式&#xff1a;f1,f2f2,f1f2 计数器&#xff1a;i 迭代表达式运算…

webpack打包配置项

webpack打包配置项 在config.js 中 module.exports {publicPath: process.env.NODE_ENV production ? / : /, //静态资源目录outputDir: dist, //打包名称assetsDir: static,//静态资源&#xff0c;目录devServer: {port: port,open: false,overlay: {warnings: false,erro…

解决Plugin ‘maven-clean-plugin:3.1.0‘ not found的问题

1. 问题描述 当导入别人的Maven项目时&#xff0c;可能会出现Plugin maven-clean-plugin:3.1.0 not found的错误信息。 2. 解决方案 2.1 方案一 检查自己的Maven仓库地址是否正确&#xff0c;一般引入其他人的项目时&#xff0c;Maven仓库的目录以及配置都会是别人的&#xff…

SpringBoot——基于Spring Task实现定时任务

目录 定时任务 项目总结 新建一个SpringBoot项目 pom.xml无需引入依赖 SpringTaskDemo SpringbootSpringtaskApplication启动类 定时任务 在日常的项目开发中&#xff0c;往往会涉及一些需要做到定时执行的代码&#xff0c;例如自动将超过24小时的未付款的订单改为取消状…

go语言,golang,linux,unbantu安装

查看系统是arm还是amd uname -m 命令可以显示系统的架构类型&#xff1a; uname -m输出可能是&#xff1a; x86_64&#xff1a;表示是 AMD64 架构&#xff08;即 64 位的 x86 架构&#xff09;。aarch64&#xff1a;表示是 ARM64 架构&#xff08;即 64 位的 ARM架构&#xf…