JavaScript | Binary Search | Thorough Explanation
Intuition\nThis is a variant of 278. First Bad Version. We can use binary search to solve this.\n\n\n# Approach\n\nThe difference from the First Bad Version is 
# Intuition\nThis is a variant of [278. First Bad Version](https://leetcode.com/problems/first-bad-version/). We can use binary search to solve this.\n\n\n# Approach\n\nThe difference from the **First Bad Version** is that we need to implement a validation function (in this case, `canBeMarked`, equivalent to the `isBadVersion` API in **First Bad Version**). \n\nTo implement `canBeMarked`, we aim to reduce the values in the `nums` array by one as much as possible at the start of the time, making the numbers undergo marking operations when they appear last in the `changeIndices`. Conversely, we can iterate from the end of `changeIndices`, marking the first occurrence of a number and adding that number to the `need` variable, representing the number of subsequent decrease operations needed. We declare a `marks` array, where each element signifies whether the corresponding element in the `nums` array has been marked. During the iteration, if the number at the index has already appeared, a decrease operation can be performed. In other words, if `need > 0`, decrement `need` by 1. If all elements in `marks` are marked, and there are no remaining decrease operations to be performed (`need === 0`), return `true`. Otherwise, return `false`.\n\nAdditionally, we need to handle 1-indexed. Here, I propose two ways to address the 1-indexed issue:\n\n- Inserting a dummy element into the beginning of the `nums` array, for example, if `nums = [3, 2, 3]` and `changeIndices = [1, 3, 2, 2, 2, 2, 3]`, after pushing a dummy element into the `nums` array, it becomes `[null, 3, 2, 3]`. In this manner, the nums array becomes a 1-indexed array, enabling correct access by `changeIndices`.\n\n- Mapping the `changeIndices` array and decreasing every element by 1. For example: `changeIndices = changeIndices.map((index) => (index - 1))`. You can also achieve this using a for loop. By doing so, you can access the nums array as a 0-indexed array as usual.\n\nHere, I present the first approach. Its advantage lies in maintaining the conventional 0-indexed convention.\n\nFinally, please note that the initial value declared for `res` is `-2`. This is because the answer is 1-indexed, so we need to add one to the index represented by `res`. If there is no valid answer during the binary search process, adding one to the initial value of `-2` results in `-1`. If you find this unconventional, a conditional statement can be used to determine the answer as well.\n\n# Complexity\n- Time complexity:\n`O(log(M) * (M + N))`. `O(log(M))` for binary search, `O(M + N)` for validation function `canBeMarked` (`O(M)` for iterating `changeIndices`, plus `O(N)` for checking `marks`).\n\n- Space complexity:\n`O(N + M)`\n\n# Code\n```\n/**\n * @param {number[]} nums\n * @param {number[]} changeIndices\n * @return {number}\n */\nvar earliestSecondToMarkIndices = function(nums, changeIndices) {\n  var changeIndices = changeIndices.map((i) => (i - 1))\n  var l = 0\n  var r = changeIndices.length - 1\n  var res = -2\n\n  var canBeMarked = (bound) => {\n    var marks = Array(nums.length).fill(false)\n    var need = 0\n    for(var i = bound; i >= 0; i--) {\n      var index = changeIndices[i]\n      if(!marks[index]) { // perform "mark" operation\n        marks[index] = true\n        need += nums[index]\n      } else {\n        // If needed, execute the "decrease" operation;\n        // otherwise, do nothing\n        if(need > 0) need--\n      }\n    }\n    return marks.every(e => e) && need === 0\n  }\n\n  while(l <= r) {\n    var m = Math.floor((l + r) / 2)\n    if(canBeMarked(m)) {\n      res = m\n      r = m - 1\n    } else {\n      l = m + 1\n    }\n  }\n  return res + 1\n};\n\n/*\n\na test case that `canBeMarked()` should return `false`:\n\nnums          [1,3]\nmark           x x\n                   v v\nchangeIndices [1,1,1,2]\n               0 1 2 3\nneed = 2\n\n*/\n```
['JavaScript']