「蓝桥·算法双周赛」第七场分级赛——小白入门赛题解

01 thanks,mom

在这里插入图片描述

#include <iostream>
using namespace std;
int main()
{
  cout<<"thanks,mom";
  return 0;
}

02 霓虹

在这里插入图片描述

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

在C++语言中,异或运算是一种二进制运算,用符号 ^ 表示。它对两个操作数进行比较,如果对应的位不同,则该位的结果为1,如果对应的位相同,则结果为0。总的来说,异或运算遵循以下规则:

0 ^ 0 = 0
0 ^ 1 = 1
1 ^ 0 = 1
1 ^ 1 = 0
#include<iostream>
using namespace std;
const int N =1e5+100;
int pos[]={0B1111110,0B0000110,0B1011011,0B1001111,0B0100111,
		   0B1101101,0B1111101,0B1000110,0B1111111,0B1101111};
		   //这是一个整数数组,包含了0到9的数字在七段LED显示屏上的表示。每个数字都是一个7位的二进制数,
		   //其中每一位代表一个特定的LED段是否亮起
char S[N],T[N];//存储输入的两个数字字符串 
inline int nu_i(int x){
	//内联函数,计算一个整数中1的个数,不断将x与1进行运算(x&1)并将x右移一位(x>>=1)来计算1的个数 
	int res =0;
	while(x){
		res+=(x & 1);
		//通过将x与1进行按位与操作(&)实现,如果x的最低位是1,x & 1的结果是1,否则是0
		x >>=1;
		//它等价于x = x >> 1
		//将x的二进制表示向右移动一位 最右边的位被丢弃
		//而最左边空出的位用x的符号位填充(对于无符号整数,左边填充0)这题只关心二进制位1的数量
	}
	return res;
}
int main(){
	cin >> S;
	cin >> T;
	int ans =0;
	for(int i=0;S[i];i++){
		ans+=nu_i(pos[S[i]-'0']^pos[T[i]-'0']);
		//对于字符串中的每个字符转换为相应的数字(s[i]-'0'),然后用pos数组找到该数字的LED显示。
		//然后对S和T相同位置的数字进行异或运算^,
		//最后调用1函数计算结果中1的个数表达改变的LED段数,最后累加输出 
	}
	cout<<ans<<'\n';
	return 0;
}

在这里插入图片描述

03 奇偶排序

在这里插入图片描述
思路:分奇数,偶数排序,或者直接组合起来排序,添加排序规则(使用自定义的排序规则(所有偶数排在奇数之前,偶数或奇数内部则按从小到大排序)对它们进行排序,然后输出排序后的结果。)

#include <bits/stdc++.h>
using namespace std;
bool customCompare(int a, int b) {//排序规则
    // 如果一个是偶数,另一个是奇数,偶数更大
    if (a % 2 == 0 && b % 2 != 0) {
        return false; // 表示 a > b,因为排序是从小到大,所以返回 false 保持顺序
    } else if (a % 2 != 0 && b % 2 == 0) {
        return true; // 奇数小于偶数,在排序中应当排在前面
    } else {
        // 如果奇偶性相同,比较数值大小
        return a < b;
    }
}
int main() {
    int N;
    cin >> N;
    vector<int> A(N);
    //vector是动态数组容器
    //创建了一个大小为 N 的整数数组,所有的整数元素都被初始化为 0
    //随后,程序中的循环将通过用户输入来填充这个 vector

    // 读取数据
    for (int i = 0; i < N; ++i) {
        cin >> A[i];
    }

    // 使用自定义的比较函数进行排序
    sort(A.begin(), A.end(), customCompare);

    // 输出排序后的数组
    for (int i = 0; i < N; ++i) {
        cout << A[i] << " ";
    }
    cout << endl;
    return 0;
}
在C++中,sort函数对元素数组进行排序,它可以接受一个可选的第三个参数——一个比较函数。这个比较函数决定了排序的具体规则。

比较函数接收两个元素作为参数(这里是int a和int b),并根据排序规则返回一个布尔值:
- 如果返回true,sort函数将认为第一个参数应该在第二个参数之前(即a该比b先出现在排序后的数组中)。
- 如果返回false,sort函数将认为第一个参数应该在第二个参数之后或保持它们当前的顺序(因为sort是稳定的排序算法)。

现在,让我们解析customCompare函数:

1. 当a是偶数而b是奇数时:

   if (a % 2 == 0 && b % 2 != 0) {
       return false;
   }

这意味着在排序后的数组中,偶数(a)不应该排在奇数(b)之前。实际上,这种情况下,我们想让奇数排在前面,但由于sort函数默认是升序排序(即数值小的在前),返回false在这里意味着我们不打乱a和b的顺序,即如果偶数a出现在奇数b前面,我们不做改变(这似乎与我们的目标矛盾,但在整个数组的上下文中,这会导致奇数整体上排在偶数前面,因为偶数之间和奇数之间还会根据它们的自然顺序被进一步排序)。

  1. 当a是奇数而b是偶数时:

    else if (a % 2 != 0 && b % 2 == 0) {
        return true;
    }
    

    这表示在排序后的数组中,奇数(a)应该排在偶数(b)之前。这与我们的目标一致——所有的奇数都排在偶数之前。

  2. 对于其他情况(即a和b都是偶数或都是奇数):

    else {
        return a < b;
    }
    

    这里我们只是简单地根据它们的值来排序,如果a小于b,则a应该排在b之前,这是标准的升序排序。

通过这种方式,customCompare函数实现了一种特殊的排序规则,即先按照奇偶性排序(所有奇数在前,所有偶数在后),然后在奇数组内和偶数组内分别按照升序排序。

04 可结合的元素对

在这里插入图片描述
在这里插入图片描述

#include <bits/stdc++.h>
using namespace std;
int main(){
	ios::sync_with_stdio(0);
	int n;
	cin>>n;
	long long ans =0;
	map<int,int> res;
	while(n--){
		int x;
		cin>>x;
		for(int i=0;i<=30;i++){
			int a=(1<<i)-x;
			if(a>=0){
				ans+=res[a];
			}
		}
		res[x]++;
	} 
	cout<<ans<<'\n';
	return 0;
}

05 兽之泪

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

#include <iostream>
#include <queue>
using namespace std;
int n,k;
const int N=1e5+100;
int a[N],b[N];
using ll =long long;
using Pair = pair<int,int>;
int main(){
	ios::sync_with_stdio(0);
	cin>>k>>n;
	for(int i=1;i<=k;i++){
		cin>>a[i]>>b[i];
	}
	ll ans1=0,ans2=1e18;

//-------不挑战最后一个怪兽
	priority_queue<Pair> q;
	for(int i=1;i<k;i++){
		q.push({-a[i],i});
	} 
	int tmp=n;
	while(tmp){
		auto x=q.top();q.pop();
		ans1+=-x.first;
		q.push({-b[x.second],x.second});
		tmp--;
	}
//------挑战最后一个怪兽
	if(n>=k){
		ans2=0;
		while(!q.empty()) q.pop();
		for(int i=1;i<=k;i++){
			ans2+=a[i];
			q.push({-b[i],i});
		}
		n-=k;
		while(n){
			auto x =q.top(); q.pop();
			ans2+=-x.first;
			q.push({-b[x.second],x.second});
			n--;
		}
	} 
	cout<<min(ans1,ans2)<<endl;
	return 0;
}

06 矩阵X

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

#include <iostream>
#include <vector>
#include <queue>
#include <cstring>
using namespace std;
int n,m,n1,m1;
const int N=1e6+100;
using ll=long long;
int a[N];
ll t[N];
int Mx[N],Mn[N];
inline int getidx(int a,int b){
	return a*m+b;
}

int main(){
	ios::sync_with_stdio(0);
	cin.tie(0);
	cout.tie(0);
	cin>>n>>m>>n1>>m1;
	for(int i=0;i<n*m;i++){
		cin>>t[i];
		a[i]=t[i];
	}
	if(n1>m1){
		for(int i=0;i<n;i++){
			for(int j=0;j<m;j++){
				a[j*n+i]=t[i*m+j];
			}
		}
		swap(n1,m1);
		swap(n,m);
	}
	for(int i=0;i<n;i++){
		t[getidx(i,0)]=a[getidx(i,0)];
		for(int j=1;j<m;j++){
			t[getidx(i,j)]=a[getidx(i,j)]+t[getidx(i,j-1)];
		}
	}
	using Pair =pair<int,int>;
	priority_queue<Pair> qx,qn;
	for(int i=0;i<n;i++){
		while(!qx.empty()) qx.pop();
		while(!qn.empty()) qn.pop();
		for(int j=0;j<m1-1;j++){
			qx.push({a[getidx(i,j)],j});
			qn.push({-a[getidx(i,j)],j});
		}
		for(int j=m1-1;j<m;j++){
			while(!qx.empty()&&qx.top().second<=j-m1) qx.pop();
			while(!qn.empty()&&qn.top().second<=j-m1) qn.pop();
			qx.push({a[getidx(i,j)],j});
			qn.push({-a[getidx(i,j)],j});
			Mx[getidx(i,j)]=qx.top().first;
			Mn[getidx(i,j)]=-qn.top().first;
		}
		
	}
	ll ans=0;
	for(int i=n1-1;i<n;i++){
		for(int j=m1-1;j<m;j++){
			ll sum=0;
			int tx=-1e9,tn=1e9;
			for(int k=0;k<n1;k++){
				tx=max(tx,Mx[getidx(i-k,j)]);
				tn=max(tn,Mn[getidx(i-k,j)]);
				if(j==m1-1)sum+=t[getidx(i-k,j)];
				else sum+=t[getidx(i-k,j)]-t[getidx(i-k,j-m1)];
				
			}
			ans=max(ans,sum*(tx-tn));
		}
	}
	cout<<ans<<'\n';
	return 0;
}
  • 20
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值