码迷,mamicode.com
首页 > 其他好文 > 详细

CF 633D【斐波那契】

时间:2018-05-31 21:08:07      阅读:188      评论:0      收藏:0      [点我收藏+]

标签:高效   text   --   bre   bool   nbsp   坑点   style   copy   

狂WA巨坑题

题意:给出n<=1000个数,能组成的类似斐波那契的数列最长长度是多少(fn=fn-1+fn-2,n>=2)

solution:看起来是一道相当高端的数论题,还是D题?我现在都没现场切过D 没想到做法就是暴力?不过暴力可证复杂度OK

感觉枚举一下前两项,一直往下找,这样用个map维护一下复杂度也是n^3logn啊

不过打个斐波那契数列的表就能发现,因为每个值范围[-1e9,1e9],所以即使数列第一个和第二个是绝对值很小的两个1也会在45项左右停止,这样的话就算50项,复杂度好像可以,不过坑点巨多

坑点1:要把0特殊拿出来,因为如果前两项是0整个数列就全都是0,绝对值不上升,毒瘤数据稳稳卡成n^3logn

坑点2:如果有0要放进去1个,因为可能会有 0,x,x,……或x,0,x……这种操作

坑点3:元素有重啊!答案数列也可能有重,所以map不能存bool要存int

坑点4:map映射元素的个数,所以在原始数组中枚举前两项要去重。如果不去重,极端情况下所有数45个一组正好一个斐波那契数列,然后重复20遍,这样n^2*45,但是不要忘了还有map logn大约是10可能会被卡(99点果然被卡)

坑点5:去完重后,注意数列前两个可以相同,前提是该数出现次数>1

有些神奇刚才unique之前没sort(不能完全去重)竟然过了。。。

 

技术分享图片
 1 #include<iostream>
 2 #include<cstdio>
 3 #include<map>
 4 #include<algorithm>
 5 using namespace std;
 6 map <int,int> M,T;//int开始写成bool了 
 7 int n,A[2020],ans;
 8 int main(){
 9     scanf("%d",&n);
10     int i,j;
11     for (i=1;i<=n;i++){
12         scanf("%d",&A[i]);
13         if (!A[i]) i--,n--,ans++;
14         else M[A[i]]++;
15     }
16     if (ans) n++,M[0]=1;//有0的话给去掉0的数列加个0 
17     sort(A+1,A+n+1);//忘了 
18     n=unique(A+1,A+n+1)-A-1;//去重提高效率 
19     for (i=1;i<=n;i++) 
20     for (i=1;i<=n;i++) for (j=1;j<=n;j++)
21       if (i==j&&M[A[i]]<2) continue;
22       //不能直接i=j就退出因为数列前两个可能一样 
23       else{
24         int cur,a1=A[i],a2=A[j],sum=2;
25         T.clear();
26         T[a1]++; T[a2]++;
27         while (1){
28             cur=a1+a2; 
29             if (T[cur]==M[cur]) break;
30             T[cur]++; a1=a2; a2=cur; sum++;
31         }
32         ans=max(ans,sum);
33     }
34     cout<<ans;
35 }
技术分享图片

CF 633D【斐波那契】

标签:高效   text   --   bre   bool   nbsp   坑点   style   copy   

原文地址:https://www.cnblogs.com/Pedestrian6/p/9118835.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!