Разбор ДВГУПС — тренировка 28

Правка ru15, от nikich340, 2017-08-14 02:43:54

А. Ярмарка оружия [реализация, математика]

Необходимо последовательно сравнить силы наборов, если текущая сила строго больше максимальной предыдущей, то обновляем максимальную и индекс лучшего набора. Вычислить силу набора можно было в нецелых числах как (сумма si, j / wi), или сохранить числитель и знаменатель дроби (sumsmax и wmax) и сравнивая с текущим набором домножить обе части на (wmax·wi). Не стоит забывать, что суммирование 105 чисел до 109 приведёт к переполнению типа integer.

Асимптотика: O(n·max(wi))

Код в нецелых числах

Код в целых числах

B. Имённо-фамильный никнейм [перебор, строки]

Любое решение сводится к тому, чтобы максимизировать подстроку в n (ведь чем больше символов мы возьмём из n, тем меньше потребуется из f).

Обозначим длину такой подстроки за k.

1) Наивное решение может проверять все подстроки строки n для поиска максимального k, после чего искать недостающий конец строки в f. Это будет работать за O(q·|n|2 + q·|f|) в теории, однако лишь в худшем частном случае, когда множество раз наблюдается значительное совпадение подстроки с первой часть строки si (пример: n = " ", f = " ", и все si = " ").

Код

2) Подсчитать все возможные подстроки для n за |n|2, сложить в set[string] или бор, или подсчитать хеши (это будет работать аналогично set[string]). Теперь для каждого si можно последовательно искать k, после чего можно пройтись последовательно по f, узнав, есть ли там оставшиеся |si| - k символов. При использовании set[string] или хешей можно также искать k бинарным поиском, укорачивая или удлиняя текущую строку до длины M на каждой итерации и ища ей соответствие в подстроках n.

Асимптотики такого решения:

  • Для хешей или set:
    • если искать k последовательно: O(q·k·log2(|n|2) + q·|f|)
    • бинарным поиском: O(q·log2(klog2(|n|2) + q·|f|)
  • Для бора: O(q·k + q·|f|)

Код с set[string], последовательная проверка k

Код с set[string], бинарный поиск по k

Код с бором

3) Развернём n, f, и si задом наперёд. Тогда нам нужно максимизировать не подстроку, а подпоследовательность в f, в этом единственное отличие от предыдущего варианта. Искать k для подпоследовательности можно только последовательно, после чего нам нужно найти в n подстроку длины |n| - k, для чего опять же следует предподсчитать все возможные подстроки для n за |n|2 и сложить их в какую-нибудь структуру.

Асимптотика решения:

  • Для хешей или set[string]: O(q·k + q·log2(|n|2))
  • Для бора: O(q·k + q·|n|)

C. Два великана [игры, математика]

Очевидно, что размер кучи от 1 до x является выигрышным для Тора, т.к. он может сломать её одним ударом.

А теперь давайте подумаем насчет n = x + 1. Если Тор сломает 1 кирпич, останется x кирпичей, и Арен победит, если Тор сломает x кирпичей, Арену останется 1 кирпич и он тоже выиграет.

Значит, куча размера x + 1 всегда является проигрышной для Тора. А это в свою очередь значит, что все кучи от x + 2 до 2x + 1 являются выигрышными — Тор может всегда сломать столько кирпичей, что Арену достанется куча размера x + 1 и тот проиграет.

Подобным образом рассуждаем дальше, применяя важное правило теории игр — если из состояния текущего игрока нет способа привести состояние в проигрышное (чтобы в нём оказался другой игрок, а текущий выиграл), значит для текущего игрока состояние проигрышное, и при оптимальной игре обеих сторон он всегда будет в проигрышном состоянии, а другой игрок наоборот, в выигрышном.

И получаем, что проигрышными для Тора являются только кучи кратные x + 1 (x + 1, 2x + 2, 3x + 3, ..). Тогда ответ на отрезке [1;n] можно найти как , обозначим это функцией f(n), тогда ответ на отрезке [L;R] равняется f(R) - f(L - 1).

Асимптотика: O(q)

Код

D. Кровожадная функция [математика]

Итак, f(x) = ax·(b + x)x·c. Нам даны три значения этой функции, давайте распишем их в полном виде:

f(0) = a0·(b + 0)0·c = 1·1·c = c f(1) = a1·(b + 1)1·c = a·(b + 1)·c f(2) = a2·(b + 2)2·c

Теги разбор, двгупс, тренировка

История

 
 
 
 
Правки
 
 
  Rev. Язык Кто Когда Δ Комментарий
ru23 Русский nikich340 2017-08-15 02:06:12 57
ru22 Русский nikich340 2017-08-14 03:38:53 0 (опубликовано)
ru21 Русский nikich340 2017-08-14 03:37:24 0
ru20 Русский nikich340 2017-08-14 03:37:24 6
ru19 Русский nikich340 2017-08-14 03:35:31 879 Мелкая правка: 'няется $x^cnt[x] % m$. Сде' -> 'няется $x^{cnt[x]} % m$. Сде'
ru18 Русский nikich340 2017-08-14 03:21:52 1685
ru17 Русский nikich340 2017-08-14 02:55:25 337 Мелкая правка: '(b + 1)$\n$\frac{f' -> '(b + 1)$\n\n$\frac{f'
ru16 Русский nikich340 2017-08-14 02:47:51 294
ru15 Русский nikich340 2017-08-14 02:43:54 387
ru14 Русский nikich340 2017-08-14 02:38:00 2110
ru13 Русский nikich340 2017-08-14 02:19:17 112
ru12 Русский nikich340 2017-08-14 02:17:37 2 Мелкая правка: 'руктуру.\nАсимптот' -> 'руктуру.\n\nАсимптот'
ru11 Русский nikich340 2017-08-14 02:16:48 72 Мелкая правка: 'решения:\n- Для хе' -> 'решения:\n\n- Для хе'
ru10 Русский nikich340 2017-08-14 02:14:24 189
ru9 Русский nikich340 2017-08-13 15:40:50 4
ru8 Русский nikich340 2017-08-13 15:39:04 139
ru7 Русский nikich340 2017-08-13 15:35:40 15
ru6 Русский nikich340 2017-08-13 15:34:54 10
ru5 Русский nikich340 2017-08-13 15:33:54 427
ru4 Русский nikich340 2017-08-13 15:20:03 2245 Мелкая правка: 'ематика]\nСледовал' -> 'ематика]\n\nСледовал'
ru3 Русский nikich340 2017-08-13 15:15:48 16
ru2 Русский nikich340 2017-08-13 15:15:20 616
ru1 Русский nikich340 2017-08-13 14:57:12 113 Первая редакция (сохранено в черновиках)