[bzoj2432]兔农
将每一个重置为0的点作为一段,那么它会导致后面为以x x为开头的斐波拿起数列的东西,那么设这一段是以x为开头,要快速转移到下一段,就可以解决这道题目
为了转移,我们要处理出下面的东西:1.求出x关于模k的逆元,也就是找到这个0原来的值,那么x*上一个数就是下一段的开头;2.通过这个值反推出这一段的长度(因为我们要求出第n个数),并通过矩阵乘法求出上一个值
当(x,k)不等于1,那么就没有逆元,也就是说不会出现特殊情况,直接矩乘即可
当(x,k)=1,通过exgcd求出逆元后,由于斐波那契数列关于模k的循环节不超过6k,预处理出每一个i满足$i\equiv f[j](mod\ k)$的最小的j即可反推出长度
当然由于n过于大,有可能要经过很多个这样的东西,但由于这样的值只有k个,因此最终会形成循环,我们只需要在循环中快速查找即可
主要思路就是这样,实现起来要注意细节(比如答案不是对k取模而是对k)和实现的方法(比如特殊的转移也可以用矩阵来转移)
1 #include<bits/stdc++.h>
2 using namespace std;
3 #define N 1000005
4 struct ji{
5 int a[3][3];
6 }s,zy1,zy2,ans;
7 int k,p,fi,ne,vis[N],las[N];
8 long long n,l[N];
9 ji cheng(ji a,ji b){
10 ji c;
11 memset(c.a,0,sizeof(c.a));
12 for(int i=0;i<3;i++)
13 for(int j=0;j<3;j++)
14 for(int k=0;k<3;k++)
15 c.a[i][j]=(c.a[i][j]+1LL*a.a[i][k]*b.a[k][j])%p;
16 return c;
17 }
18 void ksm(long long n){
19 if (!n)return;
20 ji s=zy1;
21 while (n){
22 if (n&1)ans=cheng(ans,s);
23 s=cheng(s,s);
24 n/=2;
25 }
26 }
27 int exgcd(int a,int b,int &x,int &y){
28 if (!b){
29 x=1;
30 y=0;
31 return a;
32 }
33 int t=exgcd(b,a%b,y,x);
34 y-=a/b*x;
35 return t;
36 }
37 int main(){
38 scanf("%lld%d%d",&n,&k,&p);
39 ans.a[0][0]=ans.a[1][1]=ans.a[2][2]=1;
40 s=ans;
41 zy1.a[0][1]=zy1.a[1][0]=zy1.a[1][1]=zy1.a[2][2]=1;
42 zy2=zy1;
43 zy2.a[2][0]=zy2.a[2][1]=p-1;
44 int a=1,b=1;
45 for(int i=3;;i++){
46 int c=(a+b)%k;
47 if (!vis[c]){
48 vis[c]=i;
49 las[c]=b;
50 }
51 if ((!c)&&(b==1))break;
52 a=b;
53 b=c;
54 }
55 fi=1;
56 int flag=0;
57 while (1){
58 if (exgcd(fi,k,a,b)>1)break;
59 a=(a%k+k)%k;
60 if (n<vis[a])break;
61 n-=vis[a];
62 ksm(vis[a]-1);
63 ans=cheng(ans,zy2);
64 ne=1LL*fi*las[a]%k;
65 if ((flag<2)&&(l[ne])){
66 flag++;
67 if (flag<2)swap(ans,s);
68 else{
69 swap(ans,s);
70 swap(s,zy1);
71 ksm(n/(l[ne]-n)+1);
72 n%=l[ne]-n;
73 swap(s,zy1);
74 }
75 memset(l,0,sizeof(l));
76 }
77 l[fi=ne]=n;
78 }
79 ksm(n);
80 printf("%d",(ans.a[1][0]+ans.a[2][0])%p);
81 }
[bzoj2432]兔农的更多相关文章
- 【BZOJ2432】【NOI2011】兔农(数论,矩阵快速幂)
[BZOJ2432][NOI2011]兔农(数论,矩阵快速幂) 题面 BZOJ 题解 这题\(75\)分就是送的,我什么都不想写. 先手玩一下,发现每次每次出现\(mod\ K=1\)的数之后 把它减 ...
- [BZOJ2432][Noi2011]兔农 矩阵乘法+exgcd
2432: [Noi2011]兔农 Time Limit: 10 Sec Memory Limit: 256 MB Description 农夫栋栋近年收入不景气,正在他发愁如何能多赚点钱时,他听到 ...
- BZOJ2432 [Noi2011]兔农
本文版权归ljh2000和博客园共有,欢迎转载,但须保留此声明,并给出原文链接,谢谢合作. 本文作者:ljh2000作者博客:http://www.cnblogs.com/ljh2000-jump/转 ...
- 【bzoj2432】【NOI2011】兔农
题目描述 农夫栋栋近年收入不景气,正在他发愁如何能多赚点钱时,他听到隔壁的小 朋友在讨论兔子繁殖的问题. 问题是这样的:第一个月初有一对刚出生的小兔子,经过两个月长大后,这 对兔子从第三个月开始,每个 ...
- 2432: [Noi2011]兔农 - BZOJ
Description 农夫栋栋近年收入不景气,正在他发愁如何能多赚点钱时,他听到隔壁的小朋友在讨论兔子繁殖的问题. 问题是这样的:第一个月初有一对刚出生的小兔子,经过两个月长大后,这对兔子从第三个月 ...
- BZOJ 2432 兔农
Description 农夫栋栋近年收入不景气,正在他发愁如何能多赚点钱时,他听到隔壁的小朋友在讨论兔子繁殖的问题. 问题是这样的:第一个月初有一对刚出生的小兔子,经过两个月长大后,这对兔子从第三个月 ...
- NOI2011 兔农
http://www.lydsy.com/JudgeOnline/problem.php?id=2432 感觉是day1中最难的一题,还好出题人很良心,给了75分部分分. 还是跪拜策爷吧~Orz ht ...
- 【BZOJ 2432】 [Noi2011]兔农 矩乘+数论
这道题的暴力分还是很良心嘛~~~~~ 直接刚的话我发现本蒟蒻只会暴力,矩乘根本写不出来,然后让我们找一下规律,我们发现如果我们把这个序列在mod k的意义下摆出,并且在此过程中把值为1的的数减一,我们 ...
- NOI 2011 兔农 题解
事先声明,本博客代码主要模仿accepoc,且仅针对一般如本博主一样的蒟蒻. 这道题不得不说数据良心,给了75分的水分,但剩下25分真心很难得到,因此我们就来讲一讲这剩下的25分. 首先,有数据可知他 ...
随机推荐
- After Effects 图层属性及属性组结构详解
根据结构类型的属性分类 在 After Effects 的脚本开发中,图层的属性可被区分为三种类型:PROPERTY.INDEXED_GROUP 和 NAMED_GROUP .通过使用app.proj ...
- 从零入门 Serverless | 函数计算的可观测性
作者 | 夏莞 阿里巴巴函数计算团队 本文整理自<Serverless 技术公开课>,关注"Serverless"公众号,回复"入门",即可获取 S ...
- gin 集成 consul
"github.com/hashicorp/consul/api" package initialize import ( "fmt" "github ...
- 2021能源PWN wp
babyshellcode 这题考无write泄露,write被沙盒禁用时,可以考虑延时盲注的方式获得flag,此exp可作为此类型题目模版,只需要修改部分参数即可,详细见注释 from pwn im ...
- 深入理解Java虚拟机之类加载机制篇
概述 虚拟机把描述类的数据从 Class 文件加载到内存中,并对数据进行校验.转换解析和初始化,最终形成可以被虚拟机直接使用的Java类型,就是虚拟机的类加载机制. 在Java语言里面,类型的 ...
- redis中lua脚本的简单使用
一.背景 在使用redis的过程中,发现有些时候需要原子性去操作redis命令,而redis的lua脚本正好可以实现这一功能.比如: 扣减库存操作.限流操作等等. redis的pipelining虽然 ...
- 微信小程序实现上拉和下拉加载更多
在上一篇文章中,我们知道了使用 scroll-view 可以实现上拉加载更多,但是由于 scroll-view 的限制,它无法实现下拉加载更多,这篇文章我们使用 view 组件来实现 上拉和下拉加载更 ...
- 攻防世界 杂项15.János-the-Ripper
下载附件并解压,我用的是WinHex打开,发现是PK开头,并且文件中包含一个flag.txt文件,应该就是我们所需要的flag. 把下载的附件改后缀为.zip,确实有我们需要的flag,打开后需要密码 ...
- 斐波那契数列 牛客网 剑指Offer
斐波那契数列 牛客网 剑指Offer 题目描述 大家都知道斐波那契数列,现在要求输入一个整数n,请你输出斐波那契数列的第n项(从0开始,第0项为0). n<=39 class Solution: ...
- 翻转子串 牛客网 程序员面试金典 C++ Python
反转子串 牛客网 程序员面试金典 C++ Python 题目描述 假定我们都知道非常高效的算法来检查一个单词是否为其他字符串的子串.请将这个算法编写成一个函数,给定两个字符串s1和s2,请编写代码检查 ...