Другие языки программирования и технологии
как сосчитать остаток от деления больших чисел??
2^16273 mod 21583 17^16273 mod 21583
например тебе надо посчитать a^8 mod m
(a * a * a * a * a * a * a ) mod n - так не очень красиво ))
((a^2 mod n)^2 mod n)^2 mod n
если бы 8 небыло бы степенью двойки, например 25. переводим в двоичную сист. исчисления11001=2^4 + 2^3 + 2^0
тоисть a^25 mod n = (a * a^24) mod n = (a * a^8 * a^16) mod n =
= (a * (( a^2) ^2) ^2 * ((( a^2 ) ^2 ) ^2 ) ^2 mod n =
= (((( a^2 * a ) ^2 ) ^2 ) ^2 * a) mod n
таким образом a^25 можно вычислить по формуле:
((((((( a^2 mod n ) * a ) mod n ) ^2 mod n ) ^2 mod n ) ^2 mod n ) ^2 mod n) * a * mod n
#include <iostream.h>
unsigned long qe2(unsigned long, unsigned long,
unsigned long);
int main(int argc, char* argv[])
{
unsigned long a,x,n;
cout << "a = "; cin >> a;
cout << "x = "; cin >> x;
cout << "n = "; cin >> n;
cout << "a^x mod n = " << qe2(a,x,n) << endl;
return 0;
}
unsigned long qe2(unsigned long x, unsigned long y,
unsigned long n)
{
unsigned long s, t, u;
s = 1; t = x; u = y;
while(u)
{
if (u&1) s = (s*t) % n;
u >>= 1;
t = (t*t) % n;
}
return s;
}
рекурсивный вариант:
#include <iostream.h>
unsigned long fast_exp(unsigned long x,
unsigned long y,
unsigned long N);
int main(int argc, char* argv[])
{
unsigned long a, x, N;
cout << "a = "; cin >> a;
cout << "x = "; cin >> x;
cout << "N = "; cin >> N;
cout << "a^x mod n = " << fast_exp(a,x,N) << endl;
return 0;
}
unsigned long fast_exp(unsigned long x,
unsigned long y,
unsigned long N)
{
unsigned long tmp;
if (y==1) return (x % N);
if ((y&1)==0){
tmp = fast_exp(x,y/2,N);
return ((tmp*tmp)%N);
}
else {
tmp = fast_exp(x,(y-1)/2,N);
tmp = (tmp*tmp) % N;
tmp = (tmp*x) % N;
return (tmp);
}
}
для одноразового вознесения в степень по модулю лучше рекурсивный вариант.
(a * a * a * a * a * a * a ) mod n - так не очень красиво ))
((a^2 mod n)^2 mod n)^2 mod n
если бы 8 небыло бы степенью двойки, например 25. переводим в двоичную сист. исчисления11001=2^4 + 2^3 + 2^0
тоисть a^25 mod n = (a * a^24) mod n = (a * a^8 * a^16) mod n =
= (a * (( a^2) ^2) ^2 * ((( a^2 ) ^2 ) ^2 ) ^2 mod n =
= (((( a^2 * a ) ^2 ) ^2 ) ^2 * a) mod n
таким образом a^25 можно вычислить по формуле:
((((((( a^2 mod n ) * a ) mod n ) ^2 mod n ) ^2 mod n ) ^2 mod n ) ^2 mod n) * a * mod n
#include <iostream.h>
unsigned long qe2(unsigned long, unsigned long,
unsigned long);
int main(int argc, char* argv[])
{
unsigned long a,x,n;
cout << "a = "; cin >> a;
cout << "x = "; cin >> x;
cout << "n = "; cin >> n;
cout << "a^x mod n = " << qe2(a,x,n) << endl;
return 0;
}
unsigned long qe2(unsigned long x, unsigned long y,
unsigned long n)
{
unsigned long s, t, u;
s = 1; t = x; u = y;
while(u)
{
if (u&1) s = (s*t) % n;
u >>= 1;
t = (t*t) % n;
}
return s;
}
рекурсивный вариант:
#include <iostream.h>
unsigned long fast_exp(unsigned long x,
unsigned long y,
unsigned long N);
int main(int argc, char* argv[])
{
unsigned long a, x, N;
cout << "a = "; cin >> a;
cout << "x = "; cin >> x;
cout << "N = "; cin >> N;
cout << "a^x mod n = " << fast_exp(a,x,N) << endl;
return 0;
}
unsigned long fast_exp(unsigned long x,
unsigned long y,
unsigned long N)
{
unsigned long tmp;
if (y==1) return (x % N);
if ((y&1)==0){
tmp = fast_exp(x,y/2,N);
return ((tmp*tmp)%N);
}
else {
tmp = fast_exp(x,(y-1)/2,N);
tmp = (tmp*tmp) % N;
tmp = (tmp*x) % N;
return (tmp);
}
}
для одноразового вознесения в степень по модулю лучше рекурсивный вариант.
div-целочисленное деление, какой остаток? а mod даёт числа после запятой, чего там вычислять? Гемор на С тоже лишнее, проще в регистры глянуть... или не так понял вопрос
мдэ. ну и ответы.... гугли длинную арифметику. есть стандартные алгоритмы.
Похожие вопросы
- Паскаль. Цикл While. Определить остаток от деления большего числа а на меньшее число b, не используя стандартные функции
- Деление отрицательного числа. Ассемблер
- Остаток от деления в паскале
- Особенности арифметических операций в C++, деление отрицательных чисел, вопрос ниже
- При делении отрицательного числа выводит не правильный ответ (assembler). Если беру числа 127 13 10, пишет переполнение
- что такое остаток от деления и по какой формуле он вычисляется в с++
- Почему при делении дробных чисел пишет результат 0 на С++? x1=(b+pow(d,0.5))/2/a;
- Требуется калькулятор для очень больших чисел, очень больших. Есть такой?
- C++ long double большие числа при умножении искажаются
- Паскаль ДОЛГО считывает КОД с большими числами