zoukankan      html  css  js  c++  java
  • [ZJOI2012]数列 题解 [高精]

    [ZJOI2012]数列

    Description:

    ​ 小白和小蓝在一起上数学课,下课后老师留了一道作业,求下面这个数列的通项公式:

    (a_0=0,a_1=1,a_{2i}=a_i,a_{2i+1}=a_i+a_{i+1})

    ​ 小白作为一个数学爱好者,很快就计算出了这个数列的通项公式。于是,小白告诉小蓝自己已经做出来了,但为了防止小蓝抄作业,小白并不想把公式公布出来。于是小白为了向小蓝证明自己的确做出来了此题以达到其炫耀的目的,想出了一个绝妙的方法:即让小蓝说一个正整数 (n),小白则说出 (a_n) 的值,如果当 (n) 很大时小白仍能很快的说出正确答案,这就说明小白的确得到了公式。但这个方法有一个很大的漏洞:小蓝自己不会做,没法验证小白的答案是否正确。作为小蓝的好友,你能帮帮小蓝吗?

    Input:

    ​ 输入文件第一行有且只有一个正整数 (T),表示测试数据的组数。

    ​ 接下来 (T) 行,每行一个整数 (n)

    Output:

    ​ 对于每组数据:输出一行一个整数代表 (a_n)

    Sample Input:

    3
    1
    3
    10
    

    Sample Output:

    1
    2
    3
    

    Hint:

    对于 (20\%) 的数据,(1 leq n leq 10^{8})

    对于 (50\%) 的数据,(1 leq n leq 10^{12})

    对于 (100\%) 的数据,(1 leq T leq 20, 1 leq n leq 10^{100})

    题目分析:

    我们注意到一个神奇的性质:对于两个相邻的两个数 (i,i+1) , (x imes a_i + y imes a_{i+1} = x' imes a_{i/2} + y' imes a_{i/2+1} (i/2 取下整))。于是暴力高精即可。

    每次记录当前要处理的 (i) ,若 (i) 为奇数,(i+1) 的系数加上 (i) 的系数;反之,(i) 的系数加上 (i+1) 的系数。然后 (i) 变成 (i/2),直到 (i) 等于 (0) 时结束,输出 (i+1) 对应的系数。初始时 (i=n)

    代码如下(马蜂很丑,不喜勿喷)——

    
    #include<bits/stdc++.h>
    #define Tp template<typename T>
    #define Ts template<typename Ty,typename... Ar>
    #define Reg register
    #define RI Reg int
    #define Con const
    #define CI Con int&
    #define I inline
    #define W while
    #define maxn 10005
    #define LL long long
    using namespace std;
    int T,len,len1,len2,ans[maxn],a[maxn],ans1[maxn],ans2[maxn];char s[maxn];
    inline int read(){
    	int ret=0,f=1;char ch=getchar();
    	while(!isdigit(ch)){if(ch=='-') f=-f;ch=getchar();}
    	while(isdigit(ch)) ret=(ret<<1)+(ret<<3)+ch-'0',ch=getchar();
    	return ret*f;
    }
    int main(){
    //	freopen("data.in","r",stdin); 
    	T=read();while(T--){
    		scanf("%s",s+1);len=strlen(s+1);len1=max(len1,len2);for(register int i=1;i<=len1;i++) ans1[i]=ans2[i]=0;
    		ans1[len1=1]=1,len2=0;for(register int i=1;i<=len;i++) a[i]=s[len-i+1]-'0';
    		while(len>1||a[1]){
    			if(a[1]&1){
    				for(register int i=1;i<=len1;i++) ans2[i]+=ans1[i],(ans2[i]>=10)&&(ans2[i]-=10,ans2[i+1]++);
    				int now=len1+1;while(ans2[now]>=10) ans2[now]-=10,now++,ans2[now]++;if(!ans2[now]) now--;if(now>len2) len2=now;
    				now=0;for(register int i=len;i;i--) now*=10,now+=a[i],a[i]=(now>>1),now&=1;while(len>1&&!a[len]) len--;
    			}
    			else{
    				for(register int i=1;i<=len2;i++) ans1[i]+=ans2[i],(ans1[i]>=10)&&(ans1[i]-=10,ans1[i+1]++);
    				int now=len2+1;while(ans1[now]>=10) ans1[now]-=10,now++,ans1[now]++;if(!ans1[now]) now--;if(now>len1) len1=now;
    				now=0;for(register int i=len;i;i--) now*=10,now+=a[i],a[i]=(now>>1),now&=1;while(len>1&&!a[len]) len--;
    			}
    //			for(register int i=len1;i;i--) cout<<ans1[i];cout<<'
    ';
    //			for(register int i=len2;i;i--) cout<<ans2[i];cout<<'
    ';
    		}
    		for(register int i=len2;i;i--) cout<<ans2[i];puts("");
    	}
    	return 0;
    }
    
    /*
    #include<bits/stdc++.h>
    #define Tp template<typename T>
    #define Ts template<typename Ty,typename... Ar>
    #define Reg register
    #define RI Reg int
    #define Con const
    #define CI Con int&
    #define I inline
    #define W while
    #define maxn 10005
    #define LL long long
    using namespace std;
    int T,n,x,y;
    class FileInputOutput
    {
    	private:
    		static const int S=1<<21;
    		#define tc() (A==B&&(B=(A=Fin)+fread(Fin,1,S,stdin),A==B)?EOF:*A++)
    		#define pc(ch) (Ftop!=Fend?*Ftop++=ch:(fwrite(Fout,1,S,stdout),*(Ftop=Fout)++=ch))
    		char Fin[S],Fout[S],*A,*B,*Ftop,*Fend; int pt[25];
    	public:
    		FileInputOutput(void) { Ftop=Fout; Fend=Fout+S; }
    		Tp inline void read(T& x)
    		{
    			x=0; char ch; while (!isdigit(ch=tc()));
    			while (x=(x<<3)+(x<<1)+(ch&15),isdigit(ch=tc()));
    		}
    		Tp inline void write(T x,const char& ch)
    		{
    			if (x<0) pc('-'),x=-x; RI ptop=0; while (pt[++ptop]=x%10,x/=10);
    			while (ptop) pc(pt[ptop--]+48); pc(ch);
    		}
    		inline void flush(void)
    		{
    			fwrite(Fout,1,Ftop-Fout,stdout);
    		}
    		#undef tc
    		#undef pc
    }F;
    int main(){
    	freopen("data.in","r",stdin); 
    	F.read(T);while(T--){F.read(n);x=1,y=0;while(n){if(n&1) y+=x;else x+=y;n>>=1;}F.write(y,'
    ');}
    	return F.flush(),0;
    }
    */
    
  • 相关阅读:
    PCI Express体系结构导读(3)- PCIE
    PCI Express体系结构导读(2)
    npm添加代理和取消代理
    流媒体压力测试rtmp&hls(含推流和拉流)
    流媒体跳坑: 03-视频会议:使用LiveRTC来做视频直播
    流媒体跳坑: 02-视频会议:Webrtc服务器
    正交调制解调(MATLAB)
    mp4文件断电保存-(关于:MP4视频文件损坏的一点想法)
    流媒体跳坑: 01-Mp4 文件解析
    centos 守护 node 进程
  • 原文地址:https://www.cnblogs.com/jiangxuancheng/p/14315450.html
Copyright © 2011-2022 走看看