#include #include #include #include #include #include #include #include #include using namespace std; typedef long long ll; typedef pair PII; typedef vector VI; typedef vector VVI; #define MP make_pair #define PB push_back #define inf 1000000007 #define rep(i,n) for(int i=0;i<(int)(n);++i) template void Fill(A (&array)[N], const T &val){ std::fill( (T*)array, (T*)(array+N), val ); } long long mod = 1000000007; long long calc(long long k,long long m){ if(m==0)return 1; if(m==1)return k%mod; long long s = calc(k,m/2); if(m%2==0){ return (s*s)%mod; }else{ long long ans; ans = (s*s)%mod; return (k*ans)%mod; } } vector prime; #define N 100000 bool arr[N]; void Eratosthenes(){ for(int i = 0; i < N; i++){ arr[i] = 1; } for(int i = 2; i < N; i++){ if(arr[i]){ prime.push_back((ll)i); for(int j = 0; i * (j + 2) < N; j++){ arr[i *(j + 2)] = 0; } } } } vector > mult(vector >&u,vector >&v,ll p){ vector >z(2,vector(2)); z[0][0] = (u[0][0]*v[0][0]+u[0][1]*v[1][0])%p; z[0][1] = (u[0][0]*v[0][1]+u[0][1]*v[1][1])%p; z[1][0] = (u[1][0]*v[0][0]+u[1][1]*v[1][0])%p; z[1][1] = (u[1][0]*v[0][1]+u[1][1]*v[1][1])%p; return z; } vector > mul(ll x,ll p){ vector > A(2,vector(2)); A[0][0]=0; A[0][1]=1; A[1][0]=1; A[1][1]=1; if(x==1){ return A; } if(x%2==0){ vector > z; z = mul(x/2,p); return mult(z,z,p); }else{ vector > z; z = mul(x/2,p); z = mult(z,z,p); return mult(z,A,p); } } ll get_period(ll p){ if(p==2)return 3; if(p==5)return 20; set d; if(p%10==1||p%10==9){ ll x = p-1; for(ll i=1;i<=sqrt(x)+1;i++){ if(x%i==0){ if(i%2==0)d.insert(i); if((x/i)%2==0)d.insert(x/i); } } }else{ ll x = 2*p+2; d.insert(x); for(ll i=1;i<=sqrt(x);i++){ if(x%i==0){ if((p+1)%i!=0)d.insert(i); if((p+1)%(x/i)!=0)d.insert(x/i); } } } for(auto x:d){ vector > A(2,vector(2)); A = mul(x,p); if(A[0][0]==1&&A[0][1]==0&&A[1][0]==0&&A[1][1]==1){ return x; } } } int main(){ int n; cin >> n; Eratosthenes(); map ans; for(int i=0;i> p >> k; ll z = get_period(p); maptmp; tmp[p]+=k-1; for(int i=0;iz)break; while(1){ if(z%prime[i]!=0)break; z/=prime[i]; tmp[prime[i]]++; } } if(z!=1){ tmp[z]++; } for(auto x:tmp){ ans[x.first] = max(ans[x.first],x.second); } } ll s=1; for(auto x:ans){ ll t = calc(x.first,x.second); s = (s*t)%mod; } cout << s << endl; return 0; }