2021.5.22 2022蓝桥杯练习赛3

Posted 斗奋力努

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了2021.5.22 2022蓝桥杯练习赛3相关的知识,希望对你有一定的参考价值。

2021.5.22 2022蓝桥杯练习赛3

闲话:
1、就难度而言,本次练习赛题目整体比较简单,要是认真补了前两场的题,应该可以轻松做完4到5题。
2、就体验而言,这场练习赛数据普遍交弱,基本上瞎搞都能过。
3、遇到不会的多问,CCSU_MI大佬,CCSU_JPanel大佬。
4、本次做题过程十分快乐。

题目
1、试题 算法训练 矩阵加法
在这里插入图片描述
解析:对应位置相加可以了,学了线代的都知道,没学的也知道。

#include<bits/stdc++.h>
using namespace std;
int main()
{
	int n,m;
	cin>>n>>m;
	int a[n+5][m+5],b[n+5][m+5],c[n+5][m+5];
	for(int i=1;i<=n;i++)
	{
		for(int j=1;j<=m;j++)
		{
			cin>>a[i][j];
		}
	}
	for(int i=1;i<=n;i++)
	{
		for(int j=1;j<=m;j++)
		{
			cin>>b[i][j];
			c[i][j]=a[i][j]+b[i][j];
		}
	}	
	for(int i=1;i<=n;i++)
	{
		for(int j=1;j<=m;j++)
		{
			cout<<c[i][j]<<" ";
		}
		cout<<endl;
	}	
}

----------------------------------------------------------------------------------------------------------------------------
2、试题 算法训练 删除多余括号
在这里插入图片描述
----------------------------------------------------------------------------------------------------------------------------
CCSU–JPanel大佬教我的硬模拟

#include<bits/stdc++.h>
#define x first
#define y second
using namespace std;
typedef pair<char,int>PLL;
string s;
bool vis[300];
stack<PLL>st;

char f(int x,int y){
    bool flag=true;
    for(int i=x+1;i<=y;i++){
        if(vis[i]==0){
            if(s[i]=='+'||s[i]=='-'){
                if(flag) return s[i];
            }
            if(s[i]=='(') flag=false;
            if(s[i]==')') flag=true;
        }
    }
    return ' ';
}

int main(){
    cin>>s;
    for(int i=0;i<s.length();i++){
        if(s[i]=='('){
            if(i==0) st.push({' ',i});
            else{
                if(s[i-1]!='('&&s[i-1]!=')') st.push({s[i-1],i});
                else st.push({' ',i});
            }
        }
        if(s[i]==')'){
            if(i!=s.length()-1){
                PLL t=st.top();
                char x=f(t.y,i);
                if(x=='+'||x=='-'){
                    if(t.x=='*'||t.x=='/'||s[i+1]=='*'||s[i+1]=='/'){
                        st.pop();
                    }
                    else{
                        if(t.x=='-'&&x=='+'){
                            st.pop();
                        }
                        else{
                            st.pop();
                            vis[t.y]=vis[i]=1;
                        }
                    }
                }
                else{
                    st.pop();
                    vis[t.y]=vis[i]=1;
                }
            }
            else{
                PLL t=st.top();
                char x=f(t.y,i);
                if(x=='+'||x=='-'){
                    if(t.x=='*'||t.x=='/'){
                        st.pop();
                    }
                    else{
                        if(t.x=='-'&&x=='+'){
                            st.pop();
                        }
                        else{
                            st.pop();
                            vis[t.y]=vis[i]=1;
                        }
                    }
                }
                else{
                    st.pop();
                    vis[t.y]=vis[i]=1;
                }
            }
        }
    }
    for(int i=0;i<s.length();i++){
        if(!vis[i]) cout<<s[i];
    }
}

----------------------------------------------------------------------------------------------------------------------------
3、试题 算法训练 邮票
在这里插入图片描述
解析:蓝桥杯数据很水,直接无脑dfs就可以了。
思路:
1、dfs(int p,int ne,int sum) 第1个参数表示位置,第2个参数表示已经贴了几张邮票,第3个参数表示当前总和(表示的数)。每次使vis[当前总和]=1
2、本题蓝桥后台数据最大数据为20,10,当n<27都可直接dfs水过。数据过大请看第二段代码。
----------------------------------------------------------------------------------------------------------------------------

#include<bits/stdc++.h>
using namespace std;
int n,m;
int a[300];
bool vis[30000];

void dfs(int p,int ne,int sum){
    if(ne>n||p>m) return;
    vis[sum]=1;
    dfs(p+1,ne,sum);
    dfs(p,ne+1,sum+a[p]);
}

int main(){
    cin>>n>>m;
    for(int i=1;i<=m;i++){
        cin>>a[i];
        vis[a[i]]=1;
    }
    dfs(1,0,0);
    for(int i=1;i<=26000;i++){
        if(!vis[i]){
            cout<<i-1<<"\\n";
            return 0;
        }
    }
}

----------------------------------------------------------------------------------------------------------------------------
CCSU__MI大佬的代码

#include<bits/stdc++.h>
using namespace std;
const int maxn = 25500 + 10;
vector<int>v;
int n, m;
int a[150];
int dp[maxn];
int main()
{
	scanf("%d%d", &n, &m);
	for (int i = 1; i <= m; i++)
	{
		scanf("%d", &a[i]);
		dp[a[i]] = 1;
	}
	sort(a + 1, a + 1 + m);
	for (int i = 1; i <= n * a[m]; i++)
	{
		if (dp[i] == 1)
		{
			v.push_back(i);
			continue;
		}
		else
		{
			int minn = INT_MAX-10;
			for (int j = 0; j < v.size(); j++)
				minn = min(minn, dp[i-v[j]]);
			if (minn + 1 > n)
			{
				printf("%d\\n", i - 1);
				break;
			}
			dp[i] = minn + 1;
		}
	}

}

----------------------------------------------------------------------------------------------------------------------------
4、试题 算法提高 贪吃的大嘴
在这里插入图片描述
解析:这个题之前应该已经讲过了,就是一个背包问题,直接套背包模板就行。

#include<bits/stdc++.h>
using namespace std;
int n,m;
int a[55],b[55],dp[20005];
bool vis[20005];
int main(){
    cin>>n>>m;
    memset(dp,0x3f3f3f3f,sizeof(dp));
    dp[0]=0;
    for(int i=1;i<=m;i++) cin>>a[i]>>b[i];
    for(int i=1;i<=m;i++){
        for(int j=0;j<b[i];j++){
            for(int k=n;k>=a[i];k--){
                dp[k]=min(dp[k],dp[k-a[i]]+1);
            }
        }
    }
    if(dp[n]==0x3f3f3f3f) cout<<"><"<<"\\n";
    else cout<<dp[n]<<"\\n";
}

----------------------------------------------------------------------------------------------------------------------------
5、试题 算法提高 超级玛丽
在这里插入图片描述
解析:裸的线性dp,没任何坑点
思路:
1、在vis数组中讲陷阱位置对应下标变成1。vis[i]=0代表位置i是空地,vis[i]=1代表位置i是陷阱。
2、因为超级玛丽无法连着跳2个单位长度,所以开始for循环一次vis数组,看看有没有连在一块的陷阱。
3、没有连在一块的陷阱。那么就开始dp。
其中dp[1]=1;
转移方程:
if(vis[i]==0) dp[i]=dp[i-1]+dp[i-2]。//第i个位置是空地
if(vis[i]==1) dp[i]=0; //第i个位置是陷阱

#include<bits/stdc++.h>
using namespace std;
int n,m;
bool vis[45];
int dp[45];
int main(){
    cin>>n>>m;
    for(int i=1;i<=m;i++){
        int x; cin>>x;
        vis[x]=1;
    }
    bool flag=0;
    for(int i=2;i<n;i++){
        if(vis[i]==1){
            if(flag==1){
                cout<<"0"<<"\\n";
                return 0;
            }
            else{
                flag=1;
            }
        }
        else flag=0;
    }
    dp[1]=1;
    for(int i=2;i<=n;i++){
        if(vis[i]==1) dp[i]=0;
        else dp[i]=dp[i-1]+dp[i-2];
    }
    cout<<dp[n]<<"\\n";
}

----------------------------------------------------------------------------------------------------------------------------
6、试题 算法提高 8皇后·改
在这里插入图片描述
解析:在经典8皇后问题上,将原来要求输出的路径改成了输出最大数字和
学习链接:八皇后问题详解(四种解法)
思路:
1、一种是将最后输出路径代码改成求值。最后sort排序输出最大值。(代码1)
2、一种是每次完成一种情况,每次max取值,然后最后输出最大值。(代码2)
----------------------------------------------------------------------------------------------------------------------------
代码1

#include<bits/stdc++.h>
using namespace std;
int ans[10],sum[100],t=0;
int a[10][10];
bool row[10],line1[20],line2[20];
void print()
{
	for(int i=1;i<=8;i++)
	{
		sum[t]+=a[i][ans[i]];
	}
	t++;
}
void f(int step)
{
	for(int i=1;i<=8;i++)
	{
		if(row[i]==false&&line1[step+i]==false&&line2[step+8-i]==false)
		{
			ans[step]=i;
			if(step==8)
			{
				print();
			}
			row[i]=true;
			line1[step+i]=true;
			line2[step+8-i]=true;
			f(step+1);
			row[i]=false;
			line1[step+i]=false;
			line2[step+8-i]=false;
		}
	}
}
int main()
{
	for(int i=1;i<=8;i++2021.5.29 2022蓝桥杯练习赛4

2021.5.14 2022蓝桥杯练习赛2

PTA2022年蓝桥杯及天梯赛赛前训练(C++练习)

2021.5.7 2022蓝桥杯练习赛1

C++练习2022年蓝桥杯选拔赛

C++练习2022年蓝桥杯第二次选拔赛