Given an array of integers, find the first missing positive integer in linear time and constant space. In other words, find the lowest positive integer that does not exist in the array. The array can contain duplicates and negative numbers as well.
For example, the input [3, 4, -1, 1] should give 2. The input [1, 2, 0] should give 3.
I did this but not able to find what is the error in my logic when taking input as 1. it is giving output as undefined instead of 2.
var firstMissingPositive = function(nums) {
nums.sort(compare);
var arr = [];
for (let i = 0; i < nums.length; i++) {
if (nums[i] > 0)
arr.push(nums[i]);
}
if (arr.length == 0)
return 1;
else {
for (let i = 0; i < arr.length; i++) {
if (!(arr[0] == 1))
return 1;
else if (i > 0)
if (!(arr[i - 1] + 1 == arr[i]))
return i + 1;
else if ((i + 1) == arr.length)
return arr[i] + 1;
else if ((arr[i] == i + 1)) // && (arr[i+1] == arr[i]+1 ))
continue;
else
return i + 1;
}
}
};
function compare(a, b) {
return a - b;
}
Output:
Since O(n) is a requirement, we'll have to prepare some hash table of possible numbers. It will just be the length of the input array (+2 why not), containing possible number 1..n. We iterate the input array and for each number we match (if applicable) it's position = value in the array of possible numbers. We set it to -1 so we won't choose it. Finally, we iterate the possible numbers that are left and pick the first one.
var firstMissingPositive = function(nums) {
var possible = [];
for (var i = 0; i < nums.length + 2; i++) {
possible.push(i);
}
for (var i = 0; i < nums.length; i++) {
var number = nums[i];
if (number <= nums.length && number > 0) {
possible[number] = -1;
}
}
for (var i = 0; i < possible.length; i++) {
if (possible[i] > 0) {
return possible[i]
}
}
};
console.log(firstMissingPositive([3, 4, -1, 1]))
console.log(firstMissingPositive([0, 1, 2]))
console.log(firstMissingPositive([1]))
Test Cases:
(6, [1,3,2,6,1,2]) returns (pairs / 2) = 5
It does get the answer the thing is that is doing more than it needs to, It is possible just add some validation to know when he is adding same reversed index but it will only give it more to do. am looking to remove the unneeded work. can it be more reliable?
function returnOcurrences(k,ar){
debugger;
const letters = [new Set(ar)];
let pairs = 0;
for (let i = 0; i < ar.length; i++) {
for (let ii = 0; ii < ar.length; ii++) {
let a = ar[i] + ar[ii];
if (i != ii) {
if (a >= k) {
pairs += (a % k == 0) ? 1 : 0
}
}
}
}
return pairs/2;
}
What I assume you want to do is prevent the algorithm from checking e.g. ar[1] + ar[2], then ar[2] + ar[1] again.
To solve this, consider starting your inner loop from i + 1 and not from 0. This prevents the mentioned scenario from happening, and also prevents the algorithm from summing an element with itself (e.g. ar[0] + ar[0]). So no need to check anymore if i is equal to ii.
Why so? Assume the first iteration of the outer loop. You are checking the sum of ar[0] with ar[1], then with ar[2], ar[3], and so on.
On the second iteration of the outer loop, you are checking sums of ar[1] with other elements of the array. However, you already checked ar[0] + ar[1] in the previous iteration. So you start with ar[1] + ar[2], where ii = i + 1 = 2.
So the code becomes:
function returnOcurrences(k,ar){
const letters = [new Set(ar)]; //I don't see the purpose of this variable but okay
var pairs = 0;
for (var i = 0; i < ar.length; i++) {
for (var ii = i + 1; ii < ar.length; ii++) {
var a = ar[i] + ar[ii];
if (a >= k) {
pairs += (a % k == 0) ? 1 : 0
}
}
}
return pairs/2;
}
Hope this helps!
Edit: 4 Years later, I think this was a poorly asked question on my part. I hope it can be useful to someone but I think its a good candidate for removal. Proceed with a grain of salt.
Suppose I have an array, and that some function iterates through a subarray of that array. Furthermore, when if the subarray includes indexes beyond the end of the array, the subarray resumes at the first index of array.
E.g., if array length is 50, and indexing starts at 0,
48 49 0 1 ...
In particular, I'm using JavaScript's Remainder operator to get from end to beginning. array[i%array.length].
While this gets me the continuous set of indexes I want, I also want to do some filtering based on index values, and if they're beyond some point, I want to exclude them. For example, keeping only indexes 'between' 48 and 1; inclusive for the start, exclusive for the end.
What I had been doing was simply filtering on a condition such as item.index >= idx && item.index < end, but this obviously doesn't work for array beginning and end.
So, as the title states, how can I efficiently check whether a given index or set of indexes are between these points?
For the purpose of this question, starting point is inclusive, end point is exclusive.
Edit: In response to downvotes, I've clarified the question and added a couple snippets. I'm omitting each detail of the problem for brevity.
Something like that should work
function checkPresence(arr, start, stop, value){
if (arr.slice(arr.indexOf(start), arr.indexOf(stop)).indexOf(value) != -1)
return true;
else return false;
}
var tab = [12, 2, 36, 14, 48, 49, 0, 1];
console.log(checkPresence(tab, 48, 1, 49));
Without some other kind of condition, this will be an infinite loop, but here's how it would be done:
for (var i = 1; someCondition; i++) {
if (i >= array.length - 1) {
i = 1;
}
// some code
}
The suggested answers were in the right direction, but didn't quite make it there. My problem was hard to articulate, so I don't blame them.
For future visitors, below is the code that accomplished what I had in mind.
Plunkr demo
/* source array */
var source = [];
for (var i = 0; i < 10; i++) {
source.push({ index: i });
}
/* target array */
var target = [];
/* initial index reference in the array; bound between 0 and length-1 */
var index = 0;
/* count of items to be 'displayed', or allocated to the subarray; with index = 0, items 0,1,2,3 will be in the subarray */
var show = 3;
/* init target */
target = source.slice(index,show);
/* specifies count of items to be replaced when updating the subarray */
var increment = 1;
var iterator = [1,2,3,4,5,6,7,8,9];
iterator.forEach(function(item,i) {
slide(increment);
});
console.log('first index should be at index: ' + iterator.length, 'actual index is: ', target[0].index);
console.log('last index should be at index: ' + (iterator.length + show - 1)%source.length, 'actual index is: ', target[target.length-1].index);
function slide(by) {
if (!by) {
by = 1;
}
var len = source.length;
var idx;
if (index + by < 0) {
idx = len - Math.abs(by);
} else if (index + by >= len) {
idx = by;
} else {
idx = index + by;
}
var start = idx + show;
var i;
var j;
for (i = idx, j = 0; i < start; i++, j++) {
var loc = target.indexOf(source[i%len]);
if (loc >= 0) {
target[loc] = { index: null };
}
target[j] = source[i%len];
}
index = (idx) > len ? idx-len : idx;
}
Let's assume I have two variables. One an array of numbers and the other the number 3. The goal is to iterate through the array of numbers and figure out which pair of numbers can be used to equal the number 3 either by being added together or subtracted.
var numbers = [-1, -1, 4, 2, 3, 5, 0]
var target = 3
for(i = 0; i < numbers.length; i++) {
}
I understand the for loop is going to go through the array of numbers but once I do that I don't understand how I can check every pair and see if they add or subtract to hit the value of 3. Is there a JavaScript method that can help?
Not sure if I understood correctly, but maybe something like this?
var numbers = [-1, -1, 4, 2, 3, 5, 0];
var target = 3;
var pairs = [];
for (i = 0; i < numbers.length; i++) {
for (j = 0; j < numbers.length; j++) {
if (j != i) {
if ((numbers[i] + numbers[j]) == target) {
pairs.push([numbers[i], numbers[j]]);
document.write(numbers[i] + " + " + numbers[j] + " = " + target + "<br>");
}
}
}
}
Basically you go through each number in the array, then loop again through all the numbers and check if their sum equals to the target.
You can test it here.
I don't think there is a JavaScript method for this, but this should work:
for(i = 0; i < numbers.length; i++) {
// calculate the difference
var diff = target - numbers[i];
// now: numbers[i] + diff === target
// do whatever you want with diff
}
for (var i = 0; i < numbers.length-1; i++){
for (var j = i+1; j < numbers.length; j++){
if(numbers[i] + numbers[j] == target || Math.abs(numbers[i] - numbers[j]) == target){
console.log(numbers[i]+" , "+numbers[j]); //Do whatever you want
}
}
}
I am trying to figure out how to find the first missing number of a sequence of numbers like this (1,2,3,5,6,9,10,15)
I want to put the first missing number, #4, into an variable for later use but don't know how to do so?
I have tried this but this only gives me the last number:
var mynumbers=new Array(1,2,3,6,9,10);
for(var i = 1; i < 32; i++) {
if(mynumbers[i] - mynumbers[i-1] != 1) {
alert("First missing number id: "+mynumbers[i]);
break;
}
}
First of all it gives me the first number after an "hole" in the numbersequence, secondly it continues to alert all numbers comming after an "hole" if I don't insert an break. I only want the first missing number of an numbersequence from 1 - 32. How do i do so?
Hoping for help and thanks in advance ;-)
How about this
var mynumbers = new Array(1,2,3,6,9,10);
var missing;
for(var i=1;i<=32;i++)
{
if(mynumbers[i-1] != i){
missing = i;
alert(missing);
break;
}
}
The O(n) solutions are easy , but this is a common interview question and often we look for O(log n) time solution. Here is the javascript code. It's basically a modified binary search.
function misingNumInSeq(source, min = 0, max = source.length - 1){
if(min >= max){
return min + 1;
}
let pivot = Math.floor((min + max)/2);
// problem is in right side. Only look at right sub array
if(source[pivot] === pivot + 1){
return misingNumInSeq(source, pivot + 1, max);
} else {
return misingNumInSeq(source, min , pivot);
}
}
Output
misingNumInSeq([1,2,3,5,6,9,10,15])
4
By if(mynumbers[i] - mynumbers[i-1] != 1), you mean to say the series will always be incrementing by 1?
var missing = (function (arr) {
var i;
for (i = 0; i < arr.length; ++i) {
if (i + arr[0] !== arr[i]) return i + arr[0];
}
if (i < 32) // if none missing inside array and not yet 32nd
return i + arr[0]; // return next
}([1,2,3,6,9,10])); // 4
alert(missing);
You're going to need the break no matter what. That's what it's there for; to stop the loop from continuing on to the end. And you should use the length of the array instead of hardcoding 32 as the end condition, because your numbers only go up to 32, but there are possibly holes in the list so there will not be 32 elements in the array.
Since you know that each element should be 1 more than the previous element, then the number in the hole is clearly mynumbers[i - 1] + 1.
var mynumbers = new Array(1,2,3,6,9,10);
for(var i = 1; i < mynumbers.length; i++) {
if(mynumbers[i] - mynumbers[i-1] != 1) {
alert("First missing number id: " + (mynumbers[i - 1] + 1));
break;
}
}
EDIT: This only holds true for the missing number not being 1. To catch that, you will need to check if (mynumbers[0] != 1)
Edit:
function findFirstMissing(array) {
for (var i = 0; i < array.length; i++) {
if (i+1 !== array[i]) {
return i+1;
}
}
}
function findFirstMissing(array) {
for (var i = 0; i < array.length; i++) {
if (array[i+1] - array[i] !== 1) {
return array[i] + 1;
}
}
}
If you do it this way then storing it in a variable is easy:
var missing = findFirstMissing(array);
const firstNonConsecutive = arr => arr.find((el, i, arr) => (arr[i] - arr[i-1]) !== 1 && i !== 0)
this solution work for an array of positive numbers.
A solution using array.reduce to find the first positive missing integer.
function solution(A) {
return [...A].sort().reduce((acc, curr, i, arr) => {
if (acc > curr) {
arr.splice(1);
return acc;
}
else if (arr[i + 1] - curr > 1 || arr.length === i + 1) {
arr.splice(1);
return curr + 1;
}
return acc;
}, 1);
}
And here are few test cases:
console.log('solution([1, 3, 6, 4, 1, 2])', solution([1, 3, 6, 4, 1, 2]) === 5)
console.log('solution([1, 3, 2, 8, 4])', solution([1, 3, 2, 8, 4]) === 5)
console.log('solution([1])', solution([1]) === 2)
console.log('solution([-1])', solution([-1]) === 1)
console.log('solution([0])', solution([0]) === 1)
console.log('solution([-1, -4, -5, -6, -190343])', solution([-1, -4, -5, -6, -190343]) === 1)
Sometimes you just want simple if you know it's a small array:
let numbers = [1,2,3,6,9,10]
let m = 0
for (const i of numbers) if (i > ++m) break
console.log(m) // 4
Works if you remove 1 from start of array:
numbers = [2,3,6,9,10]
m = 0
for (const i of numbers) if (i > ++m) break
console.log(m) // 1
If the array can be contiguous, and if so you want the next highest number, then:
numbers = [1,2,3,4,5,6,7,8,9]
m = 0
for (const i of numbers) if (i > ++m) break
if (m == Math.max(...numbers)) m++
console.log(m) // 10
Short and sweet!
//Find the missing number in a series
//output must be 12 in a table of 3 given in below series
let abc = [3, 6, 9, 15, 18, 21, 24];
var def = [],
ghi = [];
for (var i = 1; i <= abc.length; i++) {
if (i !== abc.length) {
var diff = abc[i] - abc[i - 1];
if (def.includes(diff) === false) {
def.push(diff);
} else {
ghi.push(diff);
}
}
}
var finalArr = [];
if (ghi.length > def.length) finalArr = ghi;
else finalArr = def;
var finaldiff = finalArr[0];
var finalVal = abc.find((e, i) => {
if (e !== abc.length) {
var diff = abc[i] - abc[i - 1];
return diff > finaldiff;
}
})
console.log(finalVal - diff);
for(var i = 1; i < mynumbers.length; i++) {
if(mynumbers[i] - mynumbers[i-1] != 1) {
alert("First missing number id: "+mynumbers[i-1]+1);
i = mynumbers.length; // Replace the break
}
}
If you want you can add an initial check : if (mynumbers[0] != 1) { ... }
I think this is the simplest and optimum form of just a 2-step solution.
I think no better solution can be possible for this problem than this one.
This code uses minimum no. of variables, loops, conditionals, built-in functions and all the shitty, sloppy, unnecessary code.
This code can handle array of any length.
var mynumbers = new Array(76,77,78,79,80,81,82,83,84,125);
if(mynumbers.length > 1) {
for(var i=0; i<=mynumbers.length-1; i++) {
if(mynumbers[i+1] - 1 !== mynumbers[i]) {
alert("First Missing Term is : "+parseInt(mynumbers[i]+1));
break;
}
}
}