#include "message.h" #include "futbol.h" #include <bits/stdc++.h> using namespace std; long long MOD; long long M; long long N, K; const long long MAX = 100000004; long long WW[103]; long long TT[103]; long long potega(long long a, long long pow){ if(pow == 0){ return 1; } else if(pow == 1){ return a % MOD; } long long w = potega(a, pow/2); w *= w; w %= MOD; if(pow % 2 == 1){ w *= a; w %= MOD; } return w; } long long inv(long long x){ return potega(x, MOD - 2); } long long a, b; void przedzial(long long numer){ a = ((MAX - K) * (numer - 1))/M + K; b = ((MAX - K) * numer)/M + K; // [a, b) } int main(){ std::ios_base::sync_with_stdio(0); std::cin.tie(NULL); N = GetN(); MOD = GetP(); K = GetK(); M = NumberOfNodes(); if(MyNodeId() != 0){ int numer = MyNodeId(); przedzial(numer); long long W = 1; long long X = b - a; long long T = 1; long long h; for(int i = 0; i < X; i++){ h = inv(a - K + i + 1); h *= (a + i + 1); h %= MOD; T *= h; T %= MOD; if(i != X - 1){ W *= 2; W += T; W %= MOD; } } if(X == 0){ W = 0; } long long KOD = MOD * T + W; PutLL(0, KOD); //PutLL(0, T); //PutLL(0, W); Send(0); } else { long long r; for(int i = 1; i < M; i++){ Receive(i); r = GetLL(i); TT[i] = r / MOD; WW[i] = r % MOD; } //for(int i = 1; i < M; i++){ // TT[i] = GetLL(i); // WW[i] = GetLL(i); //} long long obecne = potega(2, K); long long dwumian = 1; int q = 1; while(true){ przedzial(q); if(N < b){ break; } long long X = b - a; obecne *= potega(2, X); obecne -= WW[q] * dwumian; obecne %= MOD; if(obecne < 0){ obecne += MOD; } dwumian *= TT[q]; dwumian %= MOD; q++; } q--; przedzial(q); // teraz robie to od b do N. long long h; for(int i = b; i < N; i++){ obecne *= 2; obecne %= MOD; obecne -= dwumian; if(obecne < 0){ obecne += MOD; } h = inv(i + 1 - K); h *= i + 1; h %= MOD; dwumian *= h; dwumian %= MOD; } cout << obecne << endl; } }
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 | #include "message.h" #include "futbol.h" #include <bits/stdc++.h> using namespace std; long long MOD; long long M; long long N, K; const long long MAX = 100000004; long long WW[103]; long long TT[103]; long long potega(long long a, long long pow){ if(pow == 0){ return 1; } else if(pow == 1){ return a % MOD; } long long w = potega(a, pow/2); w *= w; w %= MOD; if(pow % 2 == 1){ w *= a; w %= MOD; } return w; } long long inv(long long x){ return potega(x, MOD - 2); } long long a, b; void przedzial(long long numer){ a = ((MAX - K) * (numer - 1))/M + K; b = ((MAX - K) * numer)/M + K; // [a, b) } int main(){ std::ios_base::sync_with_stdio(0); std::cin.tie(NULL); N = GetN(); MOD = GetP(); K = GetK(); M = NumberOfNodes(); if(MyNodeId() != 0){ int numer = MyNodeId(); przedzial(numer); long long W = 1; long long X = b - a; long long T = 1; long long h; for(int i = 0; i < X; i++){ h = inv(a - K + i + 1); h *= (a + i + 1); h %= MOD; T *= h; T %= MOD; if(i != X - 1){ W *= 2; W += T; W %= MOD; } } if(X == 0){ W = 0; } long long KOD = MOD * T + W; PutLL(0, KOD); //PutLL(0, T); //PutLL(0, W); Send(0); } else { long long r; for(int i = 1; i < M; i++){ Receive(i); r = GetLL(i); TT[i] = r / MOD; WW[i] = r % MOD; } //for(int i = 1; i < M; i++){ // TT[i] = GetLL(i); // WW[i] = GetLL(i); //} long long obecne = potega(2, K); long long dwumian = 1; int q = 1; while(true){ przedzial(q); if(N < b){ break; } long long X = b - a; obecne *= potega(2, X); obecne -= WW[q] * dwumian; obecne %= MOD; if(obecne < 0){ obecne += MOD; } dwumian *= TT[q]; dwumian %= MOD; q++; } q--; przedzial(q); // teraz robie to od b do N. long long h; for(int i = b; i < N; i++){ obecne *= 2; obecne %= MOD; obecne -= dwumian; if(obecne < 0){ obecne += MOD; } h = inv(i + 1 - K); h *= i + 1; h %= MOD; dwumian *= h; dwumian %= MOD; } cout << obecne << endl; } } |