LeetCode: Merge Sorted Array
===== Условие ===== Даны два массива целых чисел nums1 и nums2, отсортированные в неубывающем порядке, и два целых числа m и n, представляющих количество элементов в nums1 и nums2 соответственно. Требуется объединить массивы в один, отсортированный в неубывающем порядке. Функция не должна возвращать итоговый отсортированный массив, вместо этого он должен быть сохранен внутри массива nums1. Для этого nums1 имеет длину m + n, где первые m элементов обозначают элементы, которые нужно объединить, а последние n элементов имеют значение 0 и должны игнорироваться, nums2 имеет длину n.
===== Решение ===== Для решения требуется установить два индекса indm, indn на концы массивов (для nums1 на конец значимой части, то есть на m - 1) и идти по массивам в обратном порядке. На каждой итерации в конец nums1 помещаем больший из элементов nums1[indm] и nums2[indn] и уменьшаем индекс того массива, чей элемент был взят. Цикл продолжаем до тех пор, пока хотя бы один из индексов не станет меньше 0. Если индекс для nums2 < 0, то все элементы на месте (непросмотренные элементы nums1 уже в nums1). Если индекс для nums1 < 0, то просто заполняем оставшимися элементами из nums2 начало nums1.
Сложность алгоритма по времени - O(n + m), сложность по памяти - O(1).
===== Код ===== /** * @param {number[]} nums1 * @param {number} m * @param {number[]} nums2 * @param {number} n * @return {void} Do not return anything, modify nums1 in-place instead. */ const merge = function(nums1, m, nums2, n) { let mInd = m - 1; let nInd = n - 1;
let sortedInd = m + n - 1;
while (nInd >= 0 && mInd >= 0) { if (nums1[mInd] >= nums2[nInd]) { nums1[sortedInd] = nums1[mInd]; mInd–; } else { nums1[sortedInd] = nums2[nInd]; nInd–; }
sortedInd–; }
if (mInd < 0) { for (let i = 0; i <= sortedInd; i++) nums1[i] = nums2[i]; } };