Рубрики
Без рубрики

Техника скользящие алгоритмы окон

Проблема кодирования: Учитывая строку S и символ C, найдите расстояние для всех символов в Stri … Tagged с 100днемsoFCode, JavaScript, алгоритмы, SlowingWindow.

Проблема кодирования: Учитывая строку S и символ C, найдите расстояние для всех символов в строке к символу C в строке с. Вы можете предположить, что символ C появится хотя бы один раз в строке. Эта проблема была недавно спросила Uber.

Пример:

Например, дано shortest_dist ('helloworld', 'l') , вы должны вернуть [2, 1, 0, 0, 1, 2, 2, 1, 0, 1] .

Решение проблемы:

1) Техника: раздвижные окна (в этом случае два окна справа и влево)

Запуск окна и конечные указатели:

Начальные и конечные указатели окна позволяют нам пройти через цепь, увеличивая или уменьшая размер окна, в начале указатель «конец» является единственным, который увеличивается, начальный указатель сохраняет положение до этого. Чар появляется на сцене. С появлением CHAR, Pivot обновляется, размер окна и расстояния между поворотом и элементами, которые сформировали окно до этого момента, обновляются.

Измените размер окна:

Мы можем изменить размер окна, когда мы находим вхождение персонажа в. Индекс «конец» окна проходит через всю цепочку, и начало поддерживает положение, пока мы не найдем pivot = (Вступления в Чар).

Вращаться:

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

Большой O (n):

Короче говоря, могу сказать, что это решение имеет O (N * M), где «n» – это длина «ST» и «M» – это вхождения «CHAR». Таким образом, внутренний цикл просто для обновления указателя «старта» и «pivot», чем больше случаев персонажа, тем больше раз эта цикл будет работать. Наконец, O (n) – лучший шаблон для описания поведения этих алгоритмов. Мы подчеркиваем факт использования двух окон, чтобы пройти через цепочку, это уменьшается в определенной степени размер циклов обновлений.

Код:

function shortestDist(st, char) {

    let len = st.length - 1
    let [
        winLeftStart,
        winLeftEnd,
        winRightStart,
        winRightEnd
    ] = [0, 0, len, len];
    let [pivotLeft, pivotRight] = [null, null];
    let dist = [];

    while (winLeftEnd <= len) {

        /** Window Left*/
        if (st[winLeftEnd] === char) {

            pivotLeft = winLeftEnd;
            while (winLeftStart <= pivotLeft) {
                dist[winLeftStart] = pivotLeft - winLeftStart;
                ++winLeftStart;

            }

        } if (!!pivotLeft) {

            if (dist[winLeftEnd]) {
                //End when have first match in dist
                dist[winLeftEnd] =
                    dist[winLeftEnd] < winLeftEnd - pivotLeft ?
                        dist[winLeftEnd] :
                        winLeftEnd - pivotLeft;
                return dist;
            }

            dist[winLeftEnd] = winLeftEnd - pivotLeft;
        }


        /** Window right*/
        if (st[winRightEnd] === char) {

            pivotRight = winRightEnd;
            while (winRightStart >= pivotRight) {

                dist[winRightStart] = winRightStart - pivotRight;
                --winRightStart;
            }

        } else if (!!pivotRight) {

            dist[winRightEnd] = pivotRight - winRightEnd;
        }

        /** Grow Windows*/
        --winRightEnd;
        ++winLeftEnd;
    }
 return [];
}


Простой тест:

console.log(shortestDist('helloworld', 'l'))


//        h  e  l  l  o  w  o  r  l  d
// resp. [2, 1, 0, 0, 1, 2, 2, 1, 0, 1]
//        0  1  2  3  4  5  6  7  8  9

Вы можете проверить Код по @ difo23.

Оригинал: “https://dev.to/difo23/technique-sliding-windows-algorithms-55oe”