八月月赛总结

【八月月赛总结】【普及组】

作为一名渣渣,我只敢去普及组打比赛。本次成绩打了310分(满分400),得了rank3,比上次有进步,但还是有些不尽如人意。不过听说提高组四道题出错了三道,也就是说第一道题你cout<<-1,第三道题cout<<6就能打到rank2,神不神奇?
表达了对乐编造数据的赞美与肯定(手动滑稽)
/***********************************************************************************************/
T1 计算器改良
输入一个字符串,是一个一元一次方程,只包含+、-、=、未知数、常数,没有()、*、/。所有给定的一元一次方程都是合法且有解的。输出该一元一次方程的解。
保留三位小数。
样例输入
6a-5+1=2-2a
样例输出
a=0.750
思路
从右边往左边一个一个读字符,如果读到字母就将之后的数字加到未知数系数里,没有则将之后的数字加到常数项里,最后结果是常数项/未知数系数。
代码实现

#include<stdio.h>
#include<iostream>
using namespace std;
string fc;
char tgt;
int xs,val;
//将方程化为 未知数系数*未知数=数值 的形式 
int main(){
	cin>>fc;
	bool flag=true;//false在等号左,true在等号右,从右往左求解 
	bool isNum=true;//true表示当前运算的是个常数的系数 
	int tmp=0;
	int times=1;
	int tgtpos=0;
	if(fc[0]!='+'&&fc[0]!='-'){
		fc.resize(fc.length()+1); 
		for(int i=fc.length();i>=0;i--){
			if(i==0){
				fc[i]='+';
				break;
			}
			fc[i]=fc[i-1];
		}
	}
	for(int i=0;i<fc.length();i++) if(fc[i]=='=') tgtpos=i;
	if(fc[tgtpos+1]!='+'&&fc[tgtpos+1]!='-'){
		fc.resize(fc.length()+1); 
		for(int i=fc.length();i>=tgtpos+1;i--){
			if(i==tgtpos+1){
				fc[i]='+';
				break;
			}
			fc[i]=fc[i-1];
		}
	}
	for(int i=fc.length()-1;i>-1;i--){
		if(fc[i]=='='){
			flag=false;
			isNum=true;
			tmp=0;
			times=1;
			continue;
		}
		if((fc[i]<'0'||fc[i]>'9')&&fc[i]!='+'&&fc[i]!='-'){
			tgt=fc[i];
			isNum=false;
			continue;
		}
		if(fc[i]>='0'&&fc[i]<='9'){
			tmp+=times*(fc[i]-'0');
			times*=10;
			continue;
		}
		if(fc[i]=='+'||fc[i]=='-'){
			if(flag){
				//在右边,'-'号对应未知数系数+,+号对应未知数系数-,常数项仍旧 
				if(!isNum){
					if(tmp==0) tmp=1;
					if(fc[i]=='-') xs+=tmp;
					else xs-=tmp; 
				}else{
					if(fc[i]=='+') val+=tmp;
					else val-=tmp; 
				}
			}else{
				//在左边,'-'号对应常数+,+号对应常数系数-,未知数系数仍旧 
				if(isNum){
					if(fc[i]=='-') val+=tmp;
					else val-=tmp; 
				}else{
					if(tmp==0) tmp=1;
					if(fc[i]=='+') xs+=tmp;
					else xs-=tmp; 
				}
			}
			isNum=true;
			tmp=0;
			times=1;
			continue;
		}
	}
	float res=(float)val/xs;
	if(res==-0) res=0;
	printf("%c=%.3f",tgt,res);
	return 0;
}

/***********************************************************************************************/
T2糖葫芦
商店老板告诉小朋友,谁能编程解决这个问题,谁就能免费吃一个月糖葫芦。给你两个字符串,判断它们的关系。
关系一:字符个数不相等。如Tanghul和Apple
关系二:字符个数相等,每一位都对应相等,如Tanghul和Tanghul
关系三:字符个数相等,若不计大小写,每一位都对应相等,如Tanghul和tanghul
关系四:字符个数相等,但就算不计大小写也不对应相等,如Tanghu和Banana
样例输入
Tanghul tanghul
样例输出
3
思路
没什么好说的,一道基础字符串操作题,循环对着一个一个字符来对应判断就好
代码实现

#include<stdio.h>
#include<iostream>
using namespace std;
string s1,s2;
int res;
int main(){
	cin>>s1>>s2;
	if(s1.length()!=s2.length()){
		res=1;
	}else{
		bool flag2=true;
		bool flag3=true;
		bool flag4=false;
		for(int i=0;i<s1.length();i++){
			if(s1[i]!=s2[i]){
				flag2=false;
				if(s1[i]>s2[i]){
					if(s1[i]-32!=s2[i]){
						flag3=false;
						flag4=true;
					}
				}else{
					if(s1[i]+32!=s2[i]){
						flag3=false;
						flag4=true;
					}
				}
			}
		} 
		if(flag2) res=2;
		else if(flag3) res=3;
		else if(flag4) res=4;
	}
	printf("%d",res);
	return 0;
}

/***********************************************************************************************/
T3小明买苹果
就是这道题,花了我两小时,结果只拿了10分,成为了我唯一没全A的题······
小明和妈妈来到菜市场买苹果。他突然想到,如果从袋子里拿出若干个苹果来称重,会有多少种重量?
第一行,一个正整数n,有n个苹果,n<=20
第二行,n个正整数,苹果的重量。
样例输入
3
1 3 4
样例输出
6
说明
一共有1、3、4、5、7、8六种情况
思路
先求出所有的重量和,然后再查重。但如何求出所有的重量和呢?
这里有一位大神写的用位运算来求所有种类的和的算法,目前还没搞懂,关于该算法的笔记一周之内补齐。

原地址
https://zhidao.baidu.com/question/1238852882090670579.html

代码实现

#include<stdio.h>
#include<string.h>
#include<math.h>
int n,max = 0,*m,res=0;
bool* weight;
int main(){
	scanf("%d",&n);
	m=new int[n];
	for(int i=0;i<n;i++){
		scanf("%d",m+i);
		max+=m[i];
	}
	weight = new bool[max+1];
	memset(weight,false,sizeof(weight));
	//学习中
	for(int i=1;i<pow(2,n);i++){
		int ans=0;
		int j=i;
		int testNumber=i;
		int bitsPosition=0;
		while(testNumber){
			if(testNumber%2!=0)
				ans+=m[bitsPosition];
			bitsPosition++;
			testNumber=testNumber>>1;
		} 
		weight[ans]=true;
	}
	for(int i=0;i<=max;i++){
		if(weight[i]){
			res++;
		}
	}
	printf("%d",res);
	return 0;
}

/***********************************************************************************************/
T4数列分段
对于给定的一个长度为N的正整数数列A[i],现要将其分成连续的若干段,并且每段和不超过M(可以等于M),问最少能将其分成多少段使之满足要求?
第一行包含两个正整数N,M,表示了数列A[i]的长度与每段和的最大值。
第二行包含N个用空格隔开的非负整数A[i]。
样例输入
5 6
4 2 4 5 1
样例输出
3
思路
从第一个数字循环到最后一个,有一个变量"he",如果he+A[i]>M,则段数+1,he=A[i],否则的话就he+=A[i]。
代码实现

#include<stdio.h>
int N,M,res=1;//一开始就有一段
int* A;
int main(){
	scanf("%d %d",&N,&M);
	A=new int[N];
	for(int i=0;i<N;i++) scanf("%d",A+i);
	int he=0;
	for(int i=0;i<N;i++){
		if(he+A[i]>M){
			res++;
			he=A[i];
		}else{
			he+=A[i];
		}
	}
	printf("%d",res);
}

/***********************************************************************************************/

总结

本次试题一共四道,难易比例设置较好,考察重点多为基础知识,但也能有高级做法更轻松地做,同时也有第三题这种难题来拉开差距,让各个分数段的人数较为均衡,让各个层次的选手都有发挥空间,同时也能暴露出每个人自己的不足之处,明确下一阶段的目标。给出题人1024个赞!
给自己加油!争取九月月赛能AK!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值