結果
| 問題 |
No.2117 中国剰余定理入門
|
| コンテスト | |
| ユーザー |
|
| 提出日時 | 2022-11-04 21:31:38 |
| 言語 | C++14 (gcc 13.3.0 + boost 1.87.0) |
| 結果 |
AC
|
| 実行時間 | 2 ms / 2,000 ms |
| コード長 | 1,721 bytes |
| コンパイル時間 | 1,441 ms |
| コンパイル使用メモリ | 167,436 KB |
| 実行使用メモリ | 5,376 KB |
| 最終ジャッジ日時 | 2024-07-18 19:14:46 |
| 合計ジャッジ時間 | 2,162 ms |
|
ジャッジサーバーID (参考情報) |
judge1 / judge2 |
(要ログイン)
| ファイルパターン | 結果 |
|---|---|
| other | AC * 20 |
ソースコード
#include <bits/stdc++.h>
using namespace std;
using ll = long long;
using pll = pair<ll, ll>;
#define drep(i, cc, n) for (ll i = (cc); i <= (n); ++i)
#define rep(i, n) drep(i, 0, n - 1)
#define all(a) (a).begin(), (a).end()
#define pb push_back
#define fi first
#define se second
const ll MOD = 1000000007;
const ll MOD2 = 998244353;
const ll INF = 1LL << 60;
const ll MAX_N = 2e5;
// 負の数にも対応した mod
// 例えば -17 を 5 で割った余りは本当は 3 (-17 ≡ 3 (mod. 5))
// しかし単に -17 % 5 では -2 になってしまう
inline long long mod(long long a, long long m) {
return (a % m + m) % m;
}
// 拡張 Euclid の互除法
// ap + bq = gcd(a, b) となる (p, q) を求め、d = gcd(a, b) をリターンします
long long extGcd(long long a, long long b, long long &p, long long &q) {
if (b == 0) { p = 1; q = 0; return a; }
long long d = extGcd(b, a%b, q, p);
q -= a/b * p;
return d;
}
// 中国剰余定理
// リターン値を (r, m) とすると解は x ≡ r (mod. m)
// 解なしの場合は (0, -1) をリターン
pair<long long, long long> ChineseRem(long long b1, long long m1, long long b2, long long m2) {
long long p, q;
long long d = extGcd(m1, m2, p, q); // p is inv of m1/d (mod. m2/d)
if ((b2 - b1) % d != 0) return make_pair(0, -1);
long long m = m1 * (m2/d); // lcm of (m1, m2)
long long tmp = (b2 - b1) / d * p % (m2/d);
long long r = mod(b1 + m1 * tmp, m);
return make_pair(r, m);
}
int main(){
ll b1, m1, b2, m2;
cin >> m1 >> b1 >> m2 >> b2;
pll tmp = ChineseRem(b1, m1, b2, m2);
if(tmp.fi == 0 && tmp.se == -1){
cout << "NaN" << endl;
}else{
cout << tmp.fi << endl;
}
}