第十二届蓝桥杯c++ b组国赛暴力解法

前言

刚考完试现在可算有时间可以把这个坑填上了呜呜。

不过由于比赛时间距现在有一点长了,我无法保证跟当时完全一样,但是我能保证思路大体是一样的qwq。

然后代码下面的我大部分值测了样例,没有测试oj收录(也可能是我没有找到有这道题的OJ),我就只测试了样例。

下面的我也只打了我会做的。

填空题

A 带宽

在这里插入图片描述

反思

这道题这个转换其实我看了众多科技视频都会提到的,但我一直没有补充这个转换的知识,就变了一个数上去

题解

200 / 8 = 25

所以答案是25

B 纯质数

在这里插入图片描述

反思

其实这个题并不是多么难,而且代码实现也很简单

题解

题意很明显,按照题意模拟一下答案就出来了,但是如果不用线性筛的话,我初步估计要跑10min左右

#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring>
#include <cmath>
#include <sstream>

using namespace std;

int cnt_prime;
bool vis[20210605 + 10];
int primes[20200605 + 10];

void get_prime(){
    vis[1] = 1;
    vis[0] = 1;
    for(int i = 2; i <= 20210605; i++){
		if(!vis[i]){
			primes[cnt_prime++] = i;
		}
		for(int j = 0; primes[j] <= 20210605 / i; j++){
			vis[i * primes[j]] = 1;
	        if(i % primes[j] == 0) break;
		}
	}
}

int main(){
	int ans = 0;
	get_prime();
	for(int i = 0; i < cnt_prime; i++){
		stringstream ss;
		ss << primes[i];
		string s;
		ss >> s;
		int flag = 1;
        // cout << s << endl;
        for(int j = 0; j < s.size(); j++){
            // cout << (int)(s[j] - '0') << endl;
            if(vis[(int)(s[j] - '0')]){
				flag = 0;
				break;
			}
		}
		if(flag)
			ans ++;
		
	}
	cout << ans;
	return 0;
}

C 完全日期

在这里插入图片描述

反思

这种题实际上蓝桥杯每年基本上都有的,套路也一样,不是构造日期而是判断数作为日期的合法性。这两者读者只要实验一下就知道明显后者更简单

题解

#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring>
#include <cmath>
#include <sstream>

using namespace std;

bool judge(int date){
	int y = date / 10000;
	int m = date / 100 % 100;
	int d = date % 100;
	
	int flag_run = 0;
	if(y % 4 == 0){ // 判断闰年,这里面没有1000结尾的,所以不需要判断整除400的了
		flag_run = 1;
	}
	
	if(m > 12 || m < 1){
		return 0;
	}
	if(d > 31 || d < 1){
		return 0;
	}
	
	if(m == 4 || m == 6 || m == 9 || m == 11){
		if(d > 30){
			return 0;
		}
	}
	
	if(m == 2){
		if(flag_run == 1){
			if(d > 29){
				return 0;
			}
		}
		else{
			if(d > 28){
				return 0;
			}
		}
	}
	
	return 1;
}

int main(){
	int ans = 0;
	for(int i = 20010101; i <= 20211231; i++){
		if(judge(i)){
			stringstream ss;
			ss << i;
			string s;
			ss >> s;

			int summ = 0;
			for (int j = 0; j < s.size(); j++){
				summ += s[j] - '0';
			}

			int x = sqrt(summ);
			if (x * x == summ){
				ans++;
			}
		}
	}
	cout << ans;
	return 0;
}

编程题

E 大写

在这里插入图片描述

反思

直接找桌面给的api,用ctype直接转

题解

#include <iostream>
#include <ctype.h>
#include <algorithm>

using namespace std;

int main(){
	string s;
	cin >> s;
	for (int i = 0; i < s.size(); i++){
		cout << (char)toupper(s[i]);
	}
	return 0;
}

F 123

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

反思

刚拿到这个题的时候,一看数据范围,懵了,这都到了 1 0 12 10^{12} 1012级别了,直接构造加前缀和肯定炸了。

直接先写暴力吧,当时想着能把全部题的暴力写出来就行了,全部写完再回来想正解

题解

如果直接前缀和的话,能开到10的7次方的数组大约差不多能构造完。

计算一下空间,在它给定的空间内尽可能的开大吧qwq。

在这里插入图片描述

大约能开三千万左右的ll吧,差不多可以拿到40分

#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring>
#include <cmath>
#include <map>
#include <vector>
#include <set>
#include <queue>
#include <stack>
#include <sstream>
#define ll long long
#define re return
#define Endl "\n"
#define endl "\n"

using namespace std;

typedef pair<int, int> PII;

const int MAXN = 33554400;

int T;
ll s[MAXN];

void init(){
	int cnt = 1;
	int x = 1;
	for(int i = 1; cnt <= MAXN - 10; i++){
		s[cnt] = s[cnt - 1] + i;
		if(x == i){
			x ++;
			i = 0;
		}
		cnt ++;
	}
}

int main(){
	init();
	scanf("%d", &T);
	while(T--){
		int l, r;
		scanf("%d%d", &l, &r);
		printf("%lld\n", s[r] - s[l - 1]);
	}
	return 0;
}

G 异或变换

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

反思

没思路,直接暴力模拟

题解


H 二进制问题

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

反思

问1-N中有多少个数满足恰好有K个1,那么我们在N表示的二进制位数中,排列K个1之后直接判断是不是小于N即可

题解

#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>

using namespace std;

int nn;
int m;
int way[100];
int ans = 0;

void dfs(int u, int start, int n, int m){ // u是现在是看第几位,start是从哪个数开始枚举

    if(u - 1 + n - start + 1 < m) //剪枝,后面加上所有的数不够m个就不用看了
        return;

    if(u == m + 1){
    	int x = 0;
        for (int i = 1; i <= m; i++){
        	x = x + (1 << (way[i] - 1));
            // cout << way[i] << " ";
        }
        if(x <= nn)
        	ans++;
        // cout << x << endl;
        return;
    }

    for (int i = start; i <= n; i++){
            way[u] = i;
            dfs(u + 1, i + 1, n, m); //注意此时的start变为i+1了!

            way[u] = 0;
            // vis[i] = false;
    }
}

int main(){
    cin >> nn >> m;
    int cnt = 0;
    int x = nn;
    while(x){
    	x >>= 1;
    	cnt++;
    }
    dfs(1, 1, cnt, m);
    cout << ans;
    return 0;
}

I 翻转括号序列

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

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

正常括号模拟判断就可以了qwq

  • 2
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
第14届蓝桥杯青少国赛C题要求编写一个程序,输入一段英文文字,统计其中每个字母出现的次数,并按照字母表顺序输出。 首先,我们需要读入一段英文文字,可以使用输入函数进行输入。然后,我们定义一个26个大小的数,用来存储每个字母的出现次数。接下来,我们遍历输入的每个字符,并判断是否为字母。 如果为字母,则根据字母的ASCII码,减去ASCII码中字母'A'的值,得到对应的下标,将该字母的出现次数加一。最后,我们按照字母的顺序进行输出。可以使用循环遍历整个数,如果某个字母的出现次数不为0,则输出该字母及其出现次数。 具体代码实现如下: ```python # 定义一个26个大小的数 count = [0] * 26 # 输入一段英文文字 sentence = input("请输入一段英文文字:") # 统计每个字母出现的次数 for ch in sentence: # 判断是否为字母 if ch.isalpha(): # 统计字母出现次数 index = ord(ch.lower()) - ord('a') count[index] += 1 # 按照字母表顺序输出结果 for i in range(26): # 判断某个字母的出现次数是否不为0 if count[i] != 0: # 输出字母及其出现次数 print(chr(ord('a') + i) + ":" + str(count[i]) + "次") ``` 通过以上代码,我们可以实现输入一段英文文字,然后统计其中每个字母出现的次数,并按照字母表顺序输出。这样我们就完成了第14届蓝桥杯青少国赛C题的解答。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值