Теорема. Для двух целых
чисел x и k всегда существуют такие целые p и q,
что
x = p + q
Это довольно
известная теорема, но мы не просим Вас её доказывать. Мы хотим Вас попросить
сделать кое-что попроще! Зная значения целых x и k, Вы должны найти
такие целые p и q, которые удовлетворяют заданному уравнению.
Вход. Первая строка содержит количество
тестов t (1 ≤ t ≤
1000). Каждая из следующих t строк содержит
два положительных целых числа x и k. Известно, что x и k не больше 108.
Выход. Для
каждого теста выведите в отдельной строке два целых числа p и q. Если существует
несколько пар чисел p и q, удовлетворяющих условию, то выведите
любую. Известно, что значения p и q являются 64-битными целыми числами.
Пример входа |
Пример выхода |
3 5 2 40 2 24444
6 |
1 1 1 1 0 6 |
расширенный
алгоритм Евклида
Если x
нацело делится на k, то = = x / k.
Выбрав p = 0, q = k, получим: 0 * (x / k) + k
* (x / k) = x.
Пусть x
не делится на k. Если n = , то m = = n + 1.
Поскольку НОД(n , m) = НОД(n , n + 1) = 1, то
исходя из расширенного алгоритма Евклида, существуют такие целые t и u,
что 1 = tn + um. Помножив равенство на x, получим x
= xtn + xum, откуда p = xt, q = xu.
В первом тесте x = 5, k = 2. Значение x
не делится на k нацело. Вычислим n = = 2, m = = 3. Решением
уравнения 2t + 3u = 1 будет пара (t, u) = (-1, 1). Умножим
уравнение на x = 5. Решением уравнения 2p + 3q = 5 будет пара (p,
q) = (5t, 5u) = (-5, 5). Имеет
место соотношение:
5 = (-5)
* + 5 * = (-5) * 2 + 5 * 3 =
-10 + 15
При вычислении
используем 64-битовый целый тип long long. Для простоты
использования переопределим тип:
typedef long
long i64;
Функция gcdext представляет
собой расширенный алгоритм Евклида.
void
gcdext(i64 a,i64 b, i64 *d, i64 *x, i64 *y)
{
i64 s;
if (b == 0)
{
*d = a; *x = 1; *y = 0;
return;
}
gcdext(b,a % b,d,x,y);
s = *y;
*y = *x - (a / b) * (*y);
*x = s;
}
Основная часть
программы. Читаем количество тестов. Для каждого теста вводим значения x
и k.
scanf("%d",&tests);
while(tests--)
{
scanf("%lld %lld",&x,&k);
Если x делится на k, то
устанавливаем p = 0, q = k.
if (x % k ==
0) { p = 0; q = k;}
else
{
Иначе вычисляем n
= и m = , запуская расширенный алгоритм Евклида. Он находит такие t
и u, что 1 = tn + um. Далее находим p = xt, q
= xu и выводим результат.
n = (int)floor(1.0
* x / k); m = (int)ceil(1.0 * x / k);
gcdext(n,m,&g,&t,&u);
p = t * x; q = u * x;
}
printf("%lld
%lld\n",p,q);
}