Submission #8518097


Source Code Expand

//#include "stdafx.h"
#include <iostream>
#include <set>
#include <queue>
#include <vector>
#include <algorithm>
#include <math.h>
#include <cmath>
#include <string>
#include <cstring>
#include <functional>
#include <climits>
#include <sstream>
#include <iomanip>
#include <map>
#include <stack>
#include <tuple>
#include <numeric>
#include <assert.h>
#include <functional>
#include <unordered_map>

using namespace std;

/*-----------------------------------------------------------------------------
 定義
 -------------------------------------------------------------------------------*/
#define REP(i, n)				for (int (i) = 0 ; (i) < (int)(n) ; ++(i))
#define REPN(i, m, n)			for (int (i) = m ; (i) < (int)(n) ; ++(i))
#define INF						2e9
#define MOD						(1000 * 1000 * 1000 + 7)
#define Ceil(x, n)				(((((x))+((n)-1))/n))		/* Nの倍数に切り上げ割り算 */
#define CeilN(x, n)				(((((x))+((n)-1))/n)*n)		/* Nの倍数に切り上げ */
#define FloorN(x, n)			((x)-(x)%(n))				/* Nの倍数に切り下げ */
#define IsOdd(x)				(((x)&0x01UL) == 0x01UL)			
#define IsEven(x)				(!IsOdd((x)))						
#define	BitSetV(Val,Bit)		((Val) |= (Bit))			
#define	BitTstV(Val,Bit)		((Val) & (Bit))				
#define ArrayLength(x)			(sizeof( x ) / sizeof( x[ 0 ]))
#define MAX_DWORD				(0xFFFFFFFF)
#define	MAX_SDWORD				((SDWORD)0x7FFFFFFF)
#define	MIN_SDWORD				((SDWORD)0x80000000)
#define	MAX_QWORD				((QWORD)0xFFFFFFFFFFFFFFFF)
#define	MIN_QWORD				((QWORD)0x0000000000000000)
#define	MAX_SQWORD				((SQWORD)0x7FFFFFFFFFFFFFFF)
#define	MIN_SQWORD				((SQWORD)0x8000000000000000)
#define M_PI					3.14159265358979323846

typedef long					SDWORD;
typedef long long				SQWORD;
typedef unsigned long			DWORD;
typedef unsigned long long int	QWORD;
typedef long long ll;
typedef pair<ll, ll>			P;

/*-----------------------------------------------------------------------------
 処理
 -------------------------------------------------------------------------------*/
// MOD階乗
ll modpow(ll data, ll pow, ll div)
{
	ll res = 1;
	data %= div;
	for(; 0 < pow; pow >>= 1) {
		if (pow & 1) {
			res = (res * data) % div;
		}
		data = (data * data) % div;
	}
	return res;
}

// 離散対数
ll discrete_log(ll data, ll b, ll div)
{
	// 1. m←sqrt(div)
	ll m = ceil(sqrt(div) + .1);
	
	// 2. 0≦j<mを満たすすべてのjについて(Baby-step):
	//  1. g(j)(mod div)を計算し、(j, g(j)(mod div))のペアをテーブルに保存する
	ll amari = 1;
	unordered_map<ll,ll> table;
	for(ll i = 0; i < m; i++){
		table[amari] = i;
		amari = (amari * data) % div;
	}

	// 3. g(−m)を計算する
	// 4. targetAmari←b
	ll inv = modpow(data, div - 1 - m, div);
	ll targetAmari = b;

	// 5. i = 0から(m − 1)まで(Giant-step):
	//  1. γがテーブルの第二要素(g(j)(mod div))に含まれるかチェックする
	//  2. もし含まれていれば、x = i(m) + jを返す
	//  3. もしそうでなければ、γ←γ⋅g(−m)とする
	for(ll i = 0; i < m; i++){
        if (table.find(targetAmari) != table.end()){
            ll j = table[targetAmari];
            return i * m + j;
        }
        targetAmari = targetAmari * inv % div;
    }

    return div;
}

int main()
{
	int x, p, a, b;
	cin >> x >> p >> a >> b;
	
	int k = b - a + 1;
	a %= (p - 1);
	b %= (p - 1);
	if ((a == 0) || (b < a) || (p - 1) <= k) {
		// (p - 1)乗→フェルマー小定理で余り1
		// (p - 1) <= K→1周したら余り1がある
		cout << 1 << endl;
		return 0;
	}

	ll kLim = 1 << 24;	// 10の7乗
	if (k < kLim) {
		// 総当たりで計算
		ll ans = p;
		ll data = modpow(x, a, p);
		for(ll i = 0; i < k; i++){
			ans = min(ans, data);
			data = (data * x) % p;
		}
		cout << ans << endl;
	} else {  
		for (int i = 1; i < p; i++) {
			ll y = discrete_log(x, i, p);
			if (y != p && y >= a && y <= b) {
				cout << i << endl;
				break;
			}
		}
	}

	return 0;
}

Submission Info

Submission Time
Task D - あまり
User parkmansor
Language C++14 (GCC 5.4.1)
Score 100
Code Size 4045 Byte
Status AC
Exec Time 352 ms
Memory 2468 KB

Judge Result

Set Name Sample All
Score / Max Score 0 / 0 100 / 100
Status
AC × 4
AC × 23
Set Name Test Cases
Sample sample_01.txt, sample_02.txt, sample_03.txt, sample_04.txt
All sample_02.txt, sample_03.txt, sample_04.txt, subtask1_00.txt, subtask1_01.txt, subtask1_02.txt, subtask1_03.txt, subtask1_04.txt, subtask1_05.txt, subtask1_06.txt, subtask1_07.txt, subtask1_08.txt, subtask1_09.txt, subtask1_10.txt, subtask1_11.txt, subtask1_12.txt, subtask1_13.txt, subtask1_14.txt, subtask1_15.txt, subtask1_16.txt, subtask1_17.txt, subtask1_18.txt, subtask1_19.txt
Case Name Status Exec Time Memory
sample_01.txt AC 1 ms 256 KB
sample_02.txt AC 1 ms 256 KB
sample_03.txt AC 8 ms 256 KB
sample_04.txt AC 1 ms 256 KB
subtask1_00.txt AC 352 ms 2468 KB
subtask1_01.txt AC 1 ms 256 KB
subtask1_02.txt AC 1 ms 256 KB
subtask1_03.txt AC 4 ms 256 KB
subtask1_04.txt AC 92 ms 256 KB
subtask1_05.txt AC 1 ms 256 KB
subtask1_06.txt AC 1 ms 256 KB
subtask1_07.txt AC 1 ms 256 KB
subtask1_08.txt AC 2 ms 256 KB
subtask1_09.txt AC 1 ms 256 KB
subtask1_10.txt AC 1 ms 256 KB
subtask1_11.txt AC 300 ms 2468 KB
subtask1_12.txt AC 1 ms 256 KB
subtask1_13.txt AC 1 ms 256 KB
subtask1_14.txt AC 1 ms 256 KB
subtask1_15.txt AC 321 ms 2340 KB
subtask1_16.txt AC 1 ms 256 KB
subtask1_17.txt AC 1 ms 256 KB
subtask1_18.txt AC 1 ms 256 KB
subtask1_19.txt AC 1 ms 256 KB