Как вычислить основную мощность башни по модулю m

Вот проблема: мне дано простое число P и число K. Мне нужно вычислить P ^ P ^ P ... k раз по модулю m.

Здесь P — простое число.

(P ^ (P ^ (P ^ P .... k times))) % m

Несколько примеров

для P = 2, K = 3, m = 3

2 ^ 2 ^ 2 % 3 = 1

для P = 5, K = 3, m = 3

5 ^ 5 ^ 5 % 3 = 2

Я могу выполнить грубую силу, но проблема в том, что числа могут стать очень большими.

вот ограничения

2 <= p < 10 ^ 8
1 <= k < 10 ^ 8 
1 <= m <= 10 ^ 8

person Atul    schedule 24.04.2017    source источник
comment
Насколько большими могут стать p и k?   -  person IVlad    schedule 24.04.2017
comment
@IVlad 2‹=p‹ 10^8 и 1 ‹= k ‹= 10^8   -  person Atul    schedule 24.04.2017
comment
Вы хотите вычислить [(p^p)^p]^p ... k times или p^(p^[p^...]...) k times?   -  person IVlad    schedule 24.04.2017
comment
Насколько большим я могу стать?   -  person Paul Hankin    schedule 24.04.2017
comment
@PaulHankin m находится в диапазоне простых чисел p.   -  person Atul    schedule 24.04.2017
comment
Задача была бы проще, если бы m было простым числом. Вы хотите использовать тот факт, что a^phi(m) = 1 mod m, если gcd(a,m) = 1.   -  person President James K. Polk    schedule 24.04.2017
comment
Я только что посмотрел видео на YouTube об этом... Как взломать криптографию   -  person Felix Castor    schedule 24.04.2017
comment
@IVlad для p = 5, k = 3 найти (5 ^ (5 ^ 5)) % m   -  person Atul    schedule 24.04.2017
comment
@JamesKPolk, к счастью, наш a является простым, поэтому m не обязательно должно быть.   -  person IVlad    schedule 24.04.2017
comment
@JamesKPolk Я думаю, что это лишь немного упрощает задачу: она сводит проблему к вычислению p^..^p (k-1 раз) mod phi(m), но когда вы пытаетесь решить это, phi(m) не будет быть премьером. Но я предполагаю, что этот подход работает, и phi(phi(...(m))) быстро уменьшится до 1.   -  person Paul Hankin    schedule 24.04.2017
comment
Отвечает ли это на ваш вопрос? Как вычислить a^^b mod m?   -  person Vesper    schedule 24.03.2021


Ответы (1)


Предполагая, что возведение в степень ассоциативно слева, это означает, что вам нужно вычислить:

[(p^p)^p]^p ... k times

Примечание: если это неверное предположение, то ваш вопрос является дубликатом этот вопрос. На самом деле у вас проще, так как p простое.


Тогда это равно:

p^(p*p*p*... k times)

Что равно:

p^(p^k)

Используя возведение в степень путем возведения в квадрат, это выполнимо в O(log p^k) = O(k log p)

Но это все равно слишком много для ваших заявленных пределов p, k < 10^8.

Чтобы сделать его лучше, вы можете использовать некоторую информацию из этого ответа Дуглас Зар:

можно сказать, что a^k mod m = a^(k mod phi(m)) mod m. Однако это не всегда верно, когда a и m не взаимно просты.

К счастью, в нашем случае a = p, а p — простое число, так что это верно.

Итак, ваша проблема сводится к вычислению:

p^(p^k mod phi(m)) mod m

Требуется два возведения в степень путем возведения в квадрат, что легко выполнимо.

См. как эффективно вычислить функцию totient:

int phi(int n)
{    
    int result = n;   // Initialize result as n

    // Consider all prime factors of n and subtract their
    // multiples from result
    for (int p=2; p*p<=n; ++p)
    {
        // Check if p is a prime factor.
        if (n % p == 0)
        {
            // If yes, then update n and result 
            while (n % p == 0)
                n /= p;
            result -= result / p;
        }
    }

    // If n has a prime factor greater than sqrt(n)
    // (There can be at-most one such prime factor)
    if (n > 1)
        result -= result / n;
    return result;
}
person Community    schedule 24.04.2017
comment
Без какой-либо дополнительной информации я думаю, что x ^ x ^ x - это x ^ (x ^ x), а НЕ (x ^ x) ^ x ... это было бы намного проще. По крайней мере, если это пишет математик, он имеет в виду первое. - person maraca; 24.04.2017
comment
@maraca да, он пояснил, что последнее. В этом случае это дубликат связанного вопроса. Я сделал свой ответ CW на случай, если кто-то заинтересуется этой версией. - person IVlad; 24.04.2017