Учитывая последовательность красных и синих шаров, найдите минимальное количество свопов, чтобы объединить цвета

Нам предоставляется строка вида: RBBR, где R - красный и B - синий.

Нам нужно найти минимальное количество свопов, необходимых для объединения цветов вместе. В приведенном выше случае ответ будет 1 для получения RRBB или BBRR.

Я чувствую, что алгоритм сортировки частично отсортированного массива был бы полезен здесь, так как простой вид дал бы нам количество свопов, но мы хотим minimum количество свопов.

Любые идеи?

Это, как утверждается, вопрос интервью Microsoft по this.

Ответ 1

Сделайте один проход над строкой и подсчитайте количество красных (#R) и количество блюзов (#B). Затем сделайте второй проход, подсчитывая количество красных в первых шарах #R (#r) и количестве синих шаров в первых шарах #B (#b). Меньшее количество (#R - #r) и (#B - #b) будет минимальным количеством необходимых свопов.

Ответ 2

Нам дана строка S, которую мы должны преобразовать в конечную строку F = R ^ a B ^ b или B ^ b R ^ a. Количество различий между S и F должно быть четным, потому что для каждого неулокального R будет добавочное неуместное B. Поэтому почему бы не найти минимальное количество различий между S и как возможное F, а разделить это на 2?

Например, вам предоставляется S = RBRRBRBR, который должен конвертироваться в RRRRRBBB
или BBBRRRRR

Сравнивая различия между S и F для каждого символа для каждой возможности, существует 4 отличия для каждой возможной финальной строки, поэтому, несмотря на минимум, 2 свопа.

Ответ 3

Посмотрите на свой пример. Вы знаете, что конечное состояние будет RRBB или BBRR. Другими словами, конечное состояние всегда nRmB или mBnR, где n - число R, а m - число o B в вашей строке. Поскольку конечное состояние определено, может быть, какой-то алгоритм поиска пути будет хорошим аргументом для этого? Как насчет рассмотрения каждого свопа как изменения состояния и мышления эвристической функции, чтобы приблизиться к количеству оставшихся перекопов. Я просто бросаю идею в воздух, но надеюсь, что это поможет.

Ответ 4

Начните с двух индексов одновременно с правого и левого конца строки. Продвиньте левый указатель, пока не найдете R. Продвиньте правый индекс назад, пока не найдете B. Поменяйте их. Повторяйте, пока левый указатель не встретит нужный индекс и не подсчитайте свопы. Затем сделайте то же самое, но посмотрите на B слева и R справа. Минимальное значение меньше, чем количество подкачек.

Ответ 5

Я думаю, что количество свопов может быть получено из числа инверсий, необходимых для сортировки вектора. Это является примером того, как делать это с вектором перестановки.

Ответ 6

Это не технический ответ, но я смотрел на это более интуитивно.

RRBBBBR можно уменьшить до RBR, так как группу R можно перемещать как один блок. Это означает, что массив действительно представляет собой только N наборов RB.

Единственное, что имеет значение, это количество N наборов блоков RB (включая неполные блоки для последнего).

  • RBR → 1 swap для перехода на RRB (2 набора блоков RB, RB и R)
  • RBRB- > 1 swap для перехода на RRBB (2 полных набора блоков RB)
  • RBRBRB- > 2 свопа, чтобы добраться до RRRBBB (3 полных набора блоков RB)
  • RBRBRBRB → 4 набора RB = 3 свопов

Итак, чтобы обобщить это, количество необходимых свопов = N наборов блока RB (включая неполные блоки) и вычесть 1.