Recurrent Function
Time Limit: 1000MS   Memory Limit: 65536K
Total Submissions: 1233   Accepted: 336

Description

Dr. Yao is involved in a secret research on the topic of the properties of recurrent function. Some of the functions in this research are in the following pattern:

in which set {ai} = {1, 2, …, d-1} and {bi} = {0, 1, …, d-1}.
We denote:

Yao's question is that, given two positive integer m and k, could you find a minimal non-negative integer x that

Input

There are several test cases. The first line of each test case contains an integer d (2≤d≤100). The second line contains 2d-1 integers: a1, …, ad-1, followed by b0, ..., bd-1. The third line contains integer m (0<m≤10100), and the forth line contains integer k (0<k≤10100). The input file ends with integer -1. 

Output

For each test case if it exists such an integer x, output the minimal one. We guarantee the answer is less than 263. Otherwise output a word "NO". 

Sample Input

2
1
1 0
4
7
2
1
0 1
100
200
-1

Sample Output

1
NO

Hint

For the first sample case, we can see that f(4)=7. And for the second one, the function is f(i)=i
 
题意:求解递归方程,该类方程在具体数学第一章中有明确介绍,这里只给结论,若要求解f(x),可以先将x转化成c进制c进制一共m位,即(xmxm-1...x1x0)c,那么有结论:
f((xmxm-1...x1x0)c)=(axmbxm-1bxm-2...bx1bx0)c
思路:结论已介绍,可以看出将x化成c进制后每一位都在进行置换操作,c进制首位用ai来置换,后面几位都用bi来置换。那么如果将k也转化成d进制,那么如果m的d进制的每一位通过不断置换之后最终与k的每一位分别相等,置换的最小次数x就是所求。
我们设最少置换x次,m的d进制的每一位各自置换到k的每一位需要ci次,并且每一位置换足够次数会产生轮回,轮回的大小记为loop(i)
那么x满足条件:
x==c1 mod(loop(1))
x==c2 mod(loop(2))
.....
x==cn mod(loop(n))
这样就是求满足上述模方程组的最小解即可。
 
AC代码:
#define _CRT_SECURE_NO_DEPRECATE
#include<iostream>
#include<cstdio>
#include<vector>
#include<algorithm>
#include<cstring>
#include<set>
#include<string>
#include<queue>
#include<cmath>
using namespace std;
#define INF 0x3f3f3f3f
const int N_MAX = +;
typedef long long ll;
// 大数类
class bign
{
#define base 1000
#define digit 3
private:
int _arr[];
int _m;
void bign::_simplify(void)
{
for (int i = ; i <= _m; i++)
{
if (i == _m && _arr[i] >= base) _m++;
_arr[i + ] += _arr[i] / base;
_arr[i] %= base;
}
}
public:
bign::bign(void) : _m() { memset(_arr, , sizeof(_arr)); }
bign::bign(int init) : _m()
{
memset(_arr, , sizeof(_arr));
_arr[] = init;
_simplify();
}
friend istream& operator >> (istream& fin, bign& a)
{
char init[]; int len, b, t;
fin >> init;
len = strlen(init); a._m = -;
for (int i = len - ; i >= ;)
{
t = , b = ;
for (int j = ; j < digit && i >= ; j++, i--)
{
t += (init[i] - '') * b;
b *= ;
}
a._arr[++a._m] = t;
}
return fin;
}
friend bign operator / (bign a, int b)
{
for (int i = a._m; i >= ; i--)
{
if (a._arr[i] < b && i == a._m && i != ) a._m--;
if (i > ) a._arr[i - ] += (a._arr[i] % b) * base;
a._arr[i] /= b;
} return a;
}
friend int operator % (bign a, int b)
{
for (int i = a._m; i >= ; i--)
{
if (i == ) return a._arr[i] % b;
else a._arr[i - ] += (a._arr[i] % b) * base;
}
}
friend bool operator == (bign a, bign b)
{
if (a._m != b._m) return false;
for (int i = ; i <= a._m; i++)
if (a._arr[i] != b._arr[i]) return false;
return true;
}
}; pair<ll,ll> trans(ll *a,ll m,ll k ) {//采用a置换,m为需要置换的数,k为m置换的终点,返回循环次和圈的大小
ll num = ;//num为从m到k的循环次数,不存在则为-1
ll tmp = m;
while (tmp!=k) {
if (num != && tmp == m) { num = -; break; }
num++;
tmp = a[tmp];
}
if (num == -)return make_pair(-, );
int loop = ;
while () {
if (loop != && tmp == k) { break; }
loop++;
tmp = a[tmp];
}
return make_pair(num,loop);
} ll gcd(ll a,ll b) {
if (b == )return a;
return gcd(b, a%b);
} ll extgcd(ll a,ll b,ll &x,ll &y) {
if (b == ) {
x = ; y = ;
return a;
}
ll ans = extgcd(b,a%b,x,y);
ll tmp = x;
x = y;
y = tmp - a / b*y;
return ans;
}
ll mod_inverse(ll a,ll m) {
ll x, y;
extgcd(a,m,x,y);
return (m + x%m) % m;
} pair<ll, ll>linear_congruence(const ll *A,const ll *B,const ll*M,const int& num) {
ll x = ,m = ;
for (int i = ; i < num;i++) {
ll a = A[i] * m, b = B[i] - A[i] * x, d = gcd(M[i], a);
if (b%d != )return make_pair(, -);
ll t = b / d*mod_inverse(a / d, M[i] / d) % (M[i] / d);
x = x + m*t;
m *= M[i] / d;
}
return make_pair((x%m+m)%m, m);
} ll d;
ll a[N_MAX], b[N_MAX];
bign k, m;
ll kd[N_MAX], md[N_MAX];//存储k和m的D进制形式
ll A[N_MAX], B[N_MAX], M[N_MAX];
int main() {
while(scanf("%lld",&d)&&d!=-) {
for (int i = ; i < d;i++)scanf("%lld",&a[i]);
for (int i = ; i < d;i++)scanf("%lld",&b[i]);
cin >> m >> k;
int num = ;
while (!(m==)) {
md[num++] = m%d;
m =m/ d;
}
int num2 = ;
while (!(k == )) {
kd[num2++] = k%d;
k = k / d;
}
if (num != num2) { puts("NO"); continue; }
pair<ll, ll>P;
bool flag = ;
for (int i = ; i < num-;i++) {
P = trans(b,md[i],kd[i]);
if (P.first == -) { puts("NO"); flag = ; break; }
A[i] = , B[i] = P.first, M[i] = P.second;
}
if (flag)continue; P = trans(a, md[num - ], kd[num - ]);
if (P.first == -) { puts("NO"); continue; }
A[num - ] = , B[num - ] = P.first, M[num - ] = P.second;
P = linear_congruence(A,B,M,num);
if(P.second==-) { puts("NO"); continue; }
else printf("%lld\n",P.first);
}
return ;
}

poj 3708 Recurrent Function的更多相关文章

  1. [转] POJ数学问题

    转自:http://blog.sina.com.cn/s/blog_6635898a0100magq.html 1.burnside定理,polya计数法 这个大家可以看brudildi的<组合 ...

  2. acm数学(转)

    这个东西先放在这吧.做过的以后会用#号标示出来 1.burnside定理,polya计数法    这个大家可以看brudildi的<组合数学>,那本书的这一章写的很详细也很容易理解.最好能 ...

  3. ACM数学

     1.burnside定理,polya计数法 这个专题我单独写了个小结,大家可以简单参考一下:polya 计数法,burnside定理小结 2.置换,置换的运算 置换的概念还是比较好理解的,< ...

  4. (转) Written Memories: Understanding, Deriving and Extending the LSTM

    R2RT   Written Memories: Understanding, Deriving and Extending the LSTM Tue 26 July 2016 When I was ...

  5. 从rnn到lstm,再到seq2seq(一)

    rnn的的公式很简单: 对于每个时刻,输入上一个时刻的隐层s和这个时刻的文本x,然后输出这个时刻的隐层s.对于输出的隐层s 做个ws+b就是这个时刻的输出y. tf.scan(fn, elems, i ...

  6. poj3708(公式化简+大数进制装换+线性同余方程组)

    刚看到这个题目,有点被吓到,毕竟自己这么弱. 分析了很久,然后发现m,k都可以唯一的用d进制表示.也就是用一个ai,和很多个bi唯一构成. 这点就是解题的关键了. 之后可以发现每次调用函数f(x),相 ...

  7. ACM数学知识体系

    在盛情收到学弟邀请给他们整理ACM数学方面的知识体系,作为学长非常认真的弄了好久,希望各学弟不辜负学长厚爱!!!非常抱歉因为电脑全盘格式化好多word.PPT都丢失,我尽量具体地给大家找到各知识点学习 ...

  8. Image Captioning 经典论文合辑

    Image Caption: Automatically describing the content of an image domain:CV+NLP Category:(by myself, y ...

  9. 通过百度echarts实现数据图表展示功能

    现在我们在工作中,在开发中都会或多或少的用到图表统计数据显示给用户.通过图表可以很直观的,直接的将数据呈现出来.这里我就介绍说一下利用百度开源的echarts图表技术实现的具体功能. 1.对于不太理解 ...

随机推荐

  1. FTP服务器建立windows与Linux的文件共享与读写操作

    centos7搭建vsftpd  2018-11-15 我们有时想要windows与Linux互传文件,就要用到vsftpd了.它仅仅在windows上面操作,就可以实现与Linux的通信,详情如下: ...

  2. 《剑指offer》39题—数组中出现次数超过一半的数字

    题目描述 数组中有一个数字出现的次数超过数组长度的一半,请找出这个数字.例如输入一个长度为9的数组{1,2,3,2,2,2,5,4,2}.由于数字2在数组中出现了5次,超过数组长度的一半,因此输出2. ...

  3. 2d游戏中求出一个向量的两个垂直向量

    function cc.exports.VerticalVector(vec)--求出两个垂直向量 local result = {} result[1] = cc.p(vec.y/vec.x,-1) ...

  4. 【卡常 bitset 分块】loj#6499. 「雅礼集训 2018 Day2」颜色

    好不容易算着块大小,裸的分块才能过随机极限数据:然而这题在线的数据都竟然是构造的…… 题目描述 有 $n$ 个数字,第 $i$ 个数字为 $a_i$. 有 $m$ 次询问,每次给出 $k_i$ 个区间 ...

  5. char与varchar的区别与联系

    char是字节类型,varcahr是字符类型 1.char(20) 存放的是字节,utf-8中文字符占三个字节,GB18030兼容GBK兼容GB2312中文字符占两个字节,ISO8859-1是拉丁字符 ...

  6. VMware虚拟网卡介绍和使用说明

    介绍VMware三种网络连接模式的详细配置及规则 版权声明:本文为博主原创文章,未经博主允许不得转载. 原文地址: https://www.cnblogs.com/poterliu/p/9455391 ...

  7. MySQL迁移升级解决方案

    任务背景 由于现有业务架构已不能满足当前业务需求,在保证数据完整的前提下,现需要将原有数据库迁移到另外一台单独的服务器上,在保证原有服务正常的情况下,将原有LAMP环境中mysql数据库版本5.6.3 ...

  8. Flask初学者:Jinja2模板

    Python的Jinja2模板,其实就是在HTML文档中使用控制语句和表达语句替换HTML文档中的变量来控制HTML的显示格式,Python的Jinja2模板可以更加灵活和方便的控制HTML的显示,而 ...

  9. poj3617 best cow line(贪心题)

    Best Cow Line Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 32687   Accepted: 8660 De ...

  10. poj 1017 装箱子问题 贪心算法

    题意:有1*1到6*6的的东西,需要用6*6的箱子将它们装起来.问:至少需要多少个6*6箱子 思路: 一个瓶子怎么装东西最多?先装石头,在装沙子,然后装水. 同样放在本题就是先装6*6然后5*5... ...