牛客多校第二场A,D,I

  • 只会3道签到题 (哭唧唧)  A run  ,D money ,I car。(发了3次了还保存不了,不发题解就可以保存了,滑稽脸)

1.A run

题解是用dp,我们是联想到了走楼梯问题,将起看成一次走1米或者走k+1米,这样用个记忆化搜索加前缀和就可以解决这个问题了。

include<iostream>
#include<cstdio> 
#include<cstring>
using namespace std;
const int maxn = 1010;
const int INF = 1<<20; 
const int mod = 1e9+7;
int q,k;
long long res[100005];
long long ssum[100005];
long long func(int i)
{
	if(res[i]!=0){
		return res[i];
	}	
	else{
		if(i<k){
			res[i]=1;
			ssum[i]=i;//
			return res[i];
		}
		if(i==k){
			res[i]=2;
			ssum[i]=i+1;//
			return res[i];
		}
		if(i==k+1){
			res[i]=3;
			ssum[i]=i+3;//
			return res[i];
		}
		res[i]=func(i-1)+func(i-k-1);
		ssum[i]=ssum[i-1]+res[i];
		return res[i];	
	}
}
int main()
{
	while(scanf("%d%d",&q,&k)!=EOF)
	{
		memset(res,0,sizeof(res));
		memset(ssum,0,sizeof(ssum));
		for(int i=1;i<=q;i++)
		{
			long long ans = 0;
			long long L,R;
			scanf("%lld%lld",&L,&R);
			if(ssum[R]!=0&&ssum[L-1]!=0&&ssum[R]-ssum[L-1]!=0){
				printf("%lld\n",(ssum[R]-ssum[L-1])%mod);
			}
			else
			{
				for(int j=L;j<=R;j++)
				{
					ans+=func(j);
				}
				printf("%lld\n",ans%mod);
			}
			
		}

	}
	return 0;
}

2.money

就是在给的数中找多段连续的上升子序列,最低点买入,最高点卖出。

#include <bits/stdc++.h>
using namespace std;
int main(){
	long long T,n;
	cin>>T;
	while(T--){
		cin>>n;
		long long a[n];
		for(long long i=0;i<n;++i)
			cin>>a[i];
		long long value=0,count=0,temp=a[0];
		
		for(long long i=0;i<n;++i){
			if(a[i]<a[i-1]&&i!=0){
				value+=a[i-1]-temp;
				if(a[i-1]-temp>0){
					count+=2;
				}
				temp=a[i];
			}
			
		}
		if(a[n-1]>temp){
			value+=a[n-1]-temp;
			count+=2;
		}
		cout<<value<<' '<<count<<endl;
	}
	return 0;
}

3.car

先考虑当方格没有破坏的时候,可以很容易得出n为偶有2*n辆,n为奇数时2*(n-1)+1辆(可以证明出来,或者找规律),接下来就是考虑被破坏的地方,然后减去相应的车辆,这个是有规律的。要小心的就是奇数时,中心十字架的位置。我写的比较繁琐,求个大佬的简单思路。

#include<bits/stdc++.h>
 
using namespace std;
int main(){
	int n,m;
	while(cin>>n>>m){	
		bool h[n+1];//记录行 
		bool l[n+1];//记录列 
		memset(h,0,sizeof(h));
		memset(l,0,sizeof(l));
		int x,y;
		if(n%2==0){
			int st=2*n;
			for(int i=0;i<m;++i){
				cin>>x>>y;
				if(h[x]==0&&l[y]==0){
					st-=2;
					h[x]=1,l[y]=1;
				}
				if(h[x]!=0&&l[y]==0){
					st-=1;
					l[y]=1;
				}
				if(h[x]==0&&l[y]!=0){
					st-=1;
					h[x]=1;
				}
			}
			cout<<st<<endl;
		}
		else{
			int st=2*(n-1);//先不考虑中间十字线上可能出现的汽车 
			for(int i=0;i<m;++i){
				cin>>x>>y;
				if(x==(n+1)/2||y==(n+1)/2){
					if(x==(n+1)/2&&y!=(n+1)/2){
						if(l[y]==0){
							st-=1;
						}
					}
					else if(y==(n+1)/2&&x!=(n+1)/2){
						if(h[x]==0){
							st-=1;
						}
					}	
					h[x]=1,l[y]=1;
				}
				else
				{
					if(h[x]==0&&l[y]==0){
						st-=2;
						h[x]=1,l[y]=1;
					}
					if(h[x]!=0&&l[y]==0){
						st-=1;
						l[y]=1;
					}
					if(h[x]==0&&l[y]!=0){
						st-=1;
						h[x]=1;
					}
						
				}
				
			}
			if(l[(n+1)/2]==1&&h[(n+1)/2]==1)
				cout<<st<<endl;
			else cout<<st+1<<endl;
		}
	}
	
	return 0;
} 

完结,撒花!!!!!!

猜你喜欢

转载自blog.csdn.net/tdd_master/article/details/81152849