zoukankan      html  css  js  c++  java
  • NOIP2016普及组

    T2

    回文日期

    题目描述】

    日常生活中,通过年、月、日这三个要素可以表示出一个唯一确定的日期。

    牛牛习惯用88位数字表示一个日期,其中,前44位代表年份,接下来22位代表月份,最后22位代表日期。显然:一个日期只有一种表示方法,而两个不同的日期的表示方法不会相同。

    牛牛认为,一个日期是回文的,当且仅当表示这个日期的88位数字是回文的。现在,牛牛想知道:在他指定的两个日期之间(包含这两个日期本身),有多少个真实存在的日期是回文的。

    【提示】

    一个88位数字是回文的,当且仅当对于所有的i(1<i<8)i(1<i<8)从左向右数的第ii个数字和第9i9−i个数字(即从右向左数的第ii个数字)是相同的。

    例如:

    ·对于2016年11月19日,用88位数字2016111920161119表示,它不是回文的。

    ·对于2010年1月2日,用88位数字2010010220100102表示,它是回文的。

    ·对于2010年10月2日,用88位数字2010100220101002表示,它不是回文的。

    每一年中都有12个月份:

    其中,11,33,55,77,88,1010,1212月每个月有3131天;44,66,99,1111月每个月有3030天;而对于22月,闰年时有2929天,平年时有2828天。

    一个年份是闰年当且仅当它满足下列两种情况其中的一种:

    1.这个年份是44的整数倍,但不是100100的整数倍;

    2.这个年份是400400的整数倍。

    例如:

    ·以下几个年份都是闰年:20002000 ,20122012 ,20162016

    ·以下几个年份是平年:19001900,20112011,2014

    【这个很简单,但是不是一个一个挨着判断的,而是直接根据每一年的年数去创造这个回文串,然后判断是不是回文串】

    #include<iostream>
    #include<cstring>
    #include<cmath>
    #include<algorithm>
    #include<stack>
    #include<cstdio>
    #include<queue>
    #include<map>
    #include<vector>
    #include<set>
    using namespace std;
    const int maxn=1010;
    const int INF=0x3fffffff;
    int d1,d2; 
    int rev(int x){
    	int op=0;
    	while(x){
    		op=op*10+x%10;
    		x/=10;
    	}
    	return op;
    }
    bool judge(int year,int x){
    	if(x/100>12) return 0;
    	if(x%100>31) return 0;
    	int month=x/100,day=x%100;
    	if(month==1||month==3||month==5||month==7||month==8||month==10||month==12) {
    		if(day<=31) return 1;
    		else return 0;
    	}
    	if(month==4||month==6||month==9||month==11) {
    		if(day<=30) return 1;
    		else return 0;
    	}
    	if(month==2){
    		if(year%400==0||(year%4==0&&year%100!=0)){
    			if(day<=29) return 1;
    			else return 0;
    	}
    	else{
    		if(day<=28) return 1;
    		else return 0;
    	}
    	}
    }
    int main(){
    	cin>>d1>>d2;
    	int y1=d1/10000,y2=d2/10000;
    	int ans=0;
    	int fan1=0,temp=y1;
    	fan1=rev(temp);
    	while(y1<=y2){
    		if(judge(y1,fan1)&&(y1*10000+fan1)<=d2&&(y1*10000+fan1)>=d1) {
    			ans++;
    			//cout<<y1*10000+fan1<<endl;
    		}
    		y1++;
    		fan1=rev(y1);
    	}
    	cout<<ans<<endl;
    return 0;
    }
    

      

    T4 魔法阵

    //我没有想到的方法。。。首先画图,看一下数据的分布,(同时看题目给出的数据范围,会有许多重复的数据)
    //然后设置循环的参数:c和l(c和d之间的间隙),会发现规律,b与a之间的间隙是2l,b与c之间的间隙至少有6l,所以总的循环就减少到了n/9
    //a,b的求法和c,d是一样的

    这里有两个循环,分别是针对d和b的,因为中间的6l是不确定的,但是在循环里面是确定的,所以要控制这两个数据的循环。

    从而分别用数组来保存这个物体作为a,b,c,d的情况数,res[m][4]

    #include<iostream>
    #include<cstring>
    #include<cmath>
    #include<algorithm>
    #include<stack>
    #include<cstdio>
    #include<queue>
    #include<map>
    #include<vector>
    #include<set>
    using namespace std;
    const int maxn=1010;
    const int INF=0x3fffffff;
    int n,m;
    int x[40010],vis[40010],res[40010][4]; 
     
     
    int a[40001];
    int main(){
    	scanf("%d %d",&n,&m);
    	for(int i=1;i<=m;i++){
    		scanf("%d",&x[i]);
    		vis[x[i]]++;
    	}
    	int ans=0;
    	for(int l=1;l<=n/9;l++){ //循环间隙 
    	ans=0; 
    		for(int d=9*l;d<=n;d++){ //求c,d 
    			int c=d-l;
    			int b=c-6*l-1;
    			ans+=vis[b-2*l]*vis[b]; //a,b的乘数
    			res[c][2]+=ans*vis[d];
    			res[d][3]+=ans*vis[c]; 
    		}
    	}
    	for(int l=1;l<=n/9;l++){
    		ans=0;
    		for(int b=n-7*l-1;b>=2*l+1;b--){ //从后往前枚举 
    			int a=b-2*l;
    			int c=b+6*l+1;
    			ans+=vis[c]*vis[c+l];
    			res[a][0]+=ans*vis[b];
    			res[b][1]+=ans*vis[a];
    		}
    	}
    	for(int i=1;i<=m;i++){
    		for(int j=0;j<4;j++){
    			printf("%d",res[x[i]][j]);
    			if(j<3) printf(" ");
    		}
    		printf("
    ");
    	}
    return 0;
    }
    
    /*
    30 8
    1 24 7 28 5 29 26 24
    */
    

      

  • 相关阅读:
    银行家算法实例(转)
    DNS中的七大资源记录介绍!(转)
    android之存储篇_SQLite数据库_让你彻底学会SQLite的使用(转)
    回顾HTML5的语义化元素
    vueJs2.0学习笔记(六)
    vueJs2.0学习笔记(五)
    vueJs的学习笔记(四)
    vueJs2.0学习笔记(三)
    vueJs的学习笔记(二)
    vueJs 2.0学习笔记(一)
  • 原文地址:https://www.cnblogs.com/shirlybaby/p/13622432.html
Copyright © 2011-2022 走看看