说好的钻石难度,结果本人菜的一地。。只有88分。。。。



前四题
十分钟AC
后两题二十分钟自闭
第五题玄学卡点不知为何

7-1 考试周

模拟即可,按照格式要求输出

#include<bits/stdc++.h>
using namespace std;
int main()
{
   
	double a,b,c;
	cin>>a>>b;
	c=a/b;
	printf("%.0lf/%.1f=%.0f",a,c,b);
} 

7-2 真的恭喜你

if比较输出

#include<bits/stdc++.h>
using namespace std;
int main()
{
   
	int n;
	cin>>n;
	if(n>=90)printf("gong xi ni kao le %d fen!",n);
	else printf("kao le %d fen bie xie qi!",n);
} 

7-3 平均成绩

1和0分别代表男女
男女成绩分别存,各自算出平均值,然后再求总平均值

#include<bits/stdc++.h>
using namespace std;
	double sum1;
	double sum2;
	double ans1;
	double ans2;
int main()
{
   
	double n;
	double a,b;
	cin>>n;
	for(int i=1;i<=n;i++)
	{
   
		cin>>a>>b;
		if(a==1)
		{
   
			sum1++;
			ans1+=b;
		 } 
		 else 
		 {
   
		 	sum2++;
		 	ans2+=b;
		 }
	}
	if(sum1==0)
	{
   
		printf("%.1lf X %.1lf",(ans1+ans2)/n,ans2/sum2);
	}
	else if(sum2==0)
	{
   
		printf("%.1lf %.1lf X",(ans1+ans2)/n,ans1/sum1);
	}
	else 
	{
   
		printf("%.1lf %.1lf %.1lf",(ans1+ans2)/n,ans1/sum1,ans2/sum2);
	 } 
} 

7-4 古风A+B

特判正负,因为“-”符号要特别一行,然后拆成单个存入数组,再从数组输出

#include<bits/stdc++.h>
using namespace std;
	double sum1;
	double sum2;
	double ans1;
	double ans2;
int w[100];
int main()
{
   
	long long a,b,c;
	cin>>a>>b;
	c=a+b;
	int ans=0;
	if(c<0)
	{
   
		
		cout<<"-"<<endl; 
		c=c*-1;
	}
	if(c==0)
	{
   
		cout<<"0";
		return 0;
	}
	while(c)
	{
   
		w[++ans]=c%10;
		c/=10;
	}
	for(int i=ans;i>=1;i--)
	{
   
		cout<<w[i]<<endl; 
	}
} 

难度开始上升

7-5 猜近似数字

注意两个数如果长度不一样直接就算错,输出“No”,
相同情况下,从最高位开始求差的绝对值,如果该位差的绝对值大于1,就算错,则输出“No”
如果有一位差的绝对值是1,则后面再出现绝对值1的情况,也算输,
也就是所有位上最多只能有一位的差绝对值是1,数量不能多,差的决定值不能大于1
但是这个题我错了一个点也不知道为什么?可能哪里我忽视了
我的代码如下(包含错误)

#include<bits/stdc++.h>
using namespace std;
double b=0,g=0;
double sum;
int sumb,sumg;
int main()
{
   
	string a,b;
	int c[1004];
	cin>>a;
	char ch=getchar();
	while(cin>>b&&b!="-1")
	{
   
	// cout<<"--"<<" "<<b<<endl;
		memset(c,0,sizeof(c));
		ch=getchar();
		if(a.length()!=b.length())cout<<"No"<<endl;
		else 
		{
   
	// cout<<"***"<<" "<<b<<endl;
			for(int i=0;i<a.length();i++)
			{
   
	// printf("b[a]-a[]=%d\n ",abs(a[i]-b[i]) ); 
				if(a[i]<b[i])	
				c[i]=b[i]-a[i];
				else 
				c[i]=a[i]-b[i];
	// cout<<" c[i]="<<c[i]<<endl;
			}
			bool f=0;
			for(int i=0;i<=a.length();i++)
			{
   
	// cout<<"i="<<i<<endl; 
				if(c[i]>1)
				{
   
					cout<<"No"<<endl;
					f=0;
					break;
					
				}
				else if(c[i]==1&&f==0)
				{
   
					f=1;
				}
				else if(c[i]==1&&f==1)
				{
   
					cout<<"No"<<endl;
				f=0;
				break;
				}
				
				
			}
			if(f==1)cout<<"Yes"<<endl;
		}
		
	}

}

正确代码:(学校的大佬)

#include<bits/stdc++.h>
 using namespace std; 
 string a,b; 
 int n; 
 bool boolean()
 {
   
  int l=a.size();
   bool f=0; for(int i=0;i<l;i++){
    
   if(abs(a[i]-b[i])==0){
    continue; 
   }
else if(abs(a[i]-b[i])==1&&f==0){
    f=1; }else return 0; }return 1; }int main(){
    cin>>a; while(1){
    cin>>b; if(b=="-1") break; if(b.size()!=a.size()){
    printf("No\n"); continue; }if(boolean()) printf("Yes\n"); else printf("No\n"); }return 0; }

7-6 随机输一次

尖子石头步的拼音第一位都不一样,所以光比第一位就可以
注意k中是每个多少局输一次,而非是第多少局输一次

**#include<bits/stdc++.h>
using namespace std;
int k[10006];
int main()
{
   
	int n;
	cin>>n;
	for(int i=1;i<=n;i++)
	cin>>k[i];
	char ch;
	ch=getchar();
	char s[13];
	int ans=1;
	int sum=0;
	bool f=0; 
	while(~scanf("%s",s))
	{
   
		sum++;
		if(ans>n)ans%=n;
		if(k[ans]+1==sum)
		{
   
			f=1;
			ans++;
			sum=0;
		// cout<<"-----"<<endl;
		}
		else f=0;
		if(s[0]=='E')break;
		if(s[0]=='C')
		{
   
			if(f==1)cout<<"JianDao"<<endl;
			else cout<<"Bu"<<endl;
		}
		else if(s[0]=='J')
		{
   
			if(f==1)cout<<"Bu"<<endl;
			else cout<<"ChuiZi"<<endl;
		}
		else if(s[0]=='B')
		{
   
			if(f==1)cout<<"ChuiZi"<<endl;
			else cout<<"JianDao"<<endl;
		}
		ch=getchar();
		
	}
	return 0;
}**

以下两题代码均来自我学校的大佬学长

7-7 阶乘的非零尾数

之前见过一个求最后一个非零尾数
数论问题,首先考虑末尾产生0的情况,只有当相乘的数的因子中出现2和5时会出现0,也就是0的数量取决于出现多少对2和5。
2和5都有时就出现一个0,所以求min(5,2)
因为在阶乘中5的数量是少于2的,所以只需要讨论因子中有多少个5就行,对于求后k位非零数,因为对于一个整数的后k位很简单,都会求,所以只需要在计算阶乘的过程中将对应数量的
2和5除去即可
比如求5!=12345=120的后两位非零数,就是在计算时将2和5去除计算341,然后mod 100即可

#include<bits/stdc++.h>
 using namespace std;
typedef long long ll; 
int num1,num2; 
int n,k; 
int main(){
    
  	cin>>n>>k; 
  	int n1=n;
  	 while(n1){
   
  	 	
    num1+=n1/5; //计算n1中因数5的个数 
	n1=n1/5; //
    
	}
	int num=num1;
	 num2=num1;
	  ll mod=pow(10,k);//求非零k位数 
	   ll sum=1;
	    for(int i=1;i<=n;i++){
    
	    
		int w=i;
		 while(w%2==0&&num1)
		 {
   
		 	
		  	w/=2;
			  num1--; 
		 }
		while(w%5==0&&num2)
		{
    
			w/=5;
			 num2--; 
		}
		sum=(sum%mod*w%mod)%mod; 
	}
		string c="%0"; 
		c=c+(char)(k+'0')+"lld"; 
		printf(c.data(),sum); 
		printf(" %d",num);
		 return 0; 
}

7-8 三足鼎立

之前做过一个类似的,是求能组成多少个三角形
暴力,肯定是不对滴,超时嘛
因为是构成三角形,也就是任何两边之差一定小于第三边
其中一个边已经给了

我们可以先排序,这样具备单调性,
枚举一个边,然后通过二分来确定第三个边的范围,在这范围内的是符合单个条件,然后反过来操作(确定第三个边,然后二分第二个边),重复部分就符合全部要求
所以最后结果除以二

#include<bits/stdc++.h>
 using namespace std;
typedef long long ll; 
int num1,num2; 
int n,k;
const int maxn=1e6+4;
int a[maxn]; 
int main(){
    
  	int n,p;
  	cin>>n>>p;
  	for(int i=0;i<n;i++)cin>>a[i];
  	sort(a,a+n);
  	ll sum=0;
  	for(int i=0;i<n;i++)
  	{
   
  		int high=lower_bound(a,a+n,a[i]+p)-a;
  		int low=upper_bound(a,a+n.abs(a[i]-p))-a;
  		int num=high-low;
  		if(i>=low&&i<=high)
  		{
   
  			num--;
  			sum++num;
		  }
		  
	}
	cout<<sum/2<<endl;
}