Quick sorting array in JavaScript - javascript

const arr = [5,3,2,6,1];
const quickSort = (arr) => {
for(let j = 0; j < arr.length; j++) {
let index = null;
let min = arr[0];
for(let i = 0; i < arr.length; i++) {
if(arr[i] < min) {
min = arr[i]
index = i
}
}
const tmp = arr[j]
arr[0] = min;
arr[index] = tmp
}
return arr;
}
console.log(quickSort(arr), 'res')
In the code above i try to sort the array using the next logic:
i compare each array element with the first one and if it is lower than the first then i swap the array elements.
Doing this i don't get the sorted array. Question: What is the issue with my code and how to fix it?

const arr = [5,3,2,6,1];
const quickSort = (arr) => {
for(let j = 0; j < arr.length; j++) {
let index = j;
let min = arr[j];
for(let i = j+1; i < arr.length; i++) {
if(arr[i] < min) {
min = arr[i]
index = i
}
}
let tmp = arr[j]
arr[j] = min;
arr[index] = tmp
}
return arr;
}

Quick sort is a divide and conquer algorithm used for sorting. If you want to view more information about it visit the wikipedia site for quick sort. Your current code does what you told it to do, which is not sorting but as you said it is comparing each element with the first one and if it is smaller it swaps them. Now, if you want to sort an array just use the built-in sort function
arr.sort();
That should sort the array. If you want to built one on your own I would suggest to pick one that best suits you from the long list of sorts.
If you are a beginner, I would suggest you to try Bubble Sort or Selection Sort, but if you feel comfortable with writing code then Quick Sort or even Merge Sort could potentially be more suitable for you.
Revieing your code, it appears that you were trying to implement a Selection sort. This code should help:
const arr = [5,3,2,6,1];
const SelectionSort = (arr) => {
for(let j = 0; j < arr.length; j++) {
let index = null;
let min = arr[j];
for(let i = j; i < arr.length; i++) {
if(arr[i] < min) {
min = arr[i]
index = i
}
}
const tmp = arr[j]
arr[j] = min;
arr[index] = tmp
}
return arr;
}
console.log(SelectionSort(arr), 'res')
Your main mistake in the code was that you started everything from index 0, but you should have initialised everything from j because you are in a loop.

Related

equivalent of python's array.pop() in javascript

I wonder if there's an easy to implement equivalent to python's array.pop() which returns the deleted element while deleting it from the array in parallel in javascript.
let nums = [2, 1, 3, 4, 5, 6];
function sortArray(nums) {
let arr = new Array();
let smallest_index;
for (let j = 0; j < nums.length; j++) {
smallest_index = find_smallest(nums);
console.log("smallest", smallest_index);
arr.push(nums.splice(smallest_index, 1).join(""));
}
return arr;
}
function find_smallest(arr) {
let smallest = arr[0];
let smallest_index = 0;
for (let i = 1; i < arr.length; i++) {
if (arr[i] < smallest) {
// console.log("this");
smallest = arr[i];
smallest_index = i;
}
}
return smallest_index;
}
it seems that if I replace javascript's (nums.splice(smallest_index, 1).join()) with python's (arr.append(nums.pop(smallest_index)) I would get a perfectly sorted array. is there a similar straightforward solution in javascript as well ?
OK, you use splice. Here's an example of the implementation below:
Array.prototype.pythonPop = function (index) {
return this.splice(index, 1)[0];
}
Now, I found the issue, you'll love the answer. So you were using num.length but your methods were augmenting the length of num array. Which is why your answer had only half the needed numbers. See code below. I cached the length prop of nums array
let nums = [2, 1, 3, 4, 5, 6];
function sortArray(nums) {
let arr = new Array();
let smallest_index;
console.log(nums)
for (let j = 0, length = nums.length; j < length; j++) {
smallest_index = find_smallest(nums);
console.log("smallest", smallest_index);
console.log(nums)
arr[j] = nums.splice(smallest_index, 1).join("");
}
return arr;
}
function find_smallest(arr) {
let smallest = arr[0];
let smallest_index = 0;
for (let i = 1; i < arr.length; i++) {
if (arr[i] < smallest) {
// console.log("this");
smallest = arr[i];
smallest_index = i;
}
}
return smallest_index;
}
console.log(sortArray(nums))

Generate new random values and store in an array

I am trying to generate two random values and store them in an array however I would like them to be different values each time a random number between 0-3 is generated.
function new_Randomvalues(n) {
var array1 = [];
for (var i = 0; i < n; i++) {
var row = Math.round(3*Math.random());
var col = Math.round(3*Math.random());
array1.push([row,col]);
}
return array1;
}
console.log(new_Randomvalues(10));
How do I edit this function where if an array of same numbers are pushed into array1 then remove those and generate 10 unique coordinates.
Help would be appreciated thanks
Per sam's question in the comments, here's the code:
function shuffle(array) {
for (var i = array.length - 1; i > 0; i--) {
var j = Math.floor(Math.random() * (i + 1));
var temp = array[i];
array[i] = array[j];
array[j] = temp;
}
}
pairs = [];
for (let i = 0; i <= 3; i++) {
for (let j = 0; j <= 3; j++) {
pairs.push([i, j]);
}
}
shuffle(pairs);
pairs = pairs.slice(0, 10);
console.log(pairs);

My browser lags when I try a loop function?

I wrote a simple nested loop function to multiply all items in an array and output the total value, but each time is I run a loop function my browser either crashes or doesn't stop loading
function multiplyAll(arr){
Let product = 1;
for(let i = 0; i <
arr.length; i++){
for(let j = 0; j <
arr[i].length; j *= product);
}
return product;
}
multiplyAll([[1], [2], [3]]);
You are creating an infinite loop here because of
for (let j = 0; j < arr[i].length; j *= product);
Here, j is always 0.
If you want to multiply all the nested value then you should do as:
function multiplyAll(arr) {
let product = 1;
for (let i = 0; i < arr.length; i++) {
for (let j = 0; j < arr[i].length; ++j)
product *= arr[i][j];
}
return product;
}
console.log(multiplyAll([[1], [2], [3]]));
If you just want to multiple all the nested value then you can simply do as:
function multiplyAll(arr) {
return arr.flat().reduce((acc, curr) => acc * curr, 1);
// If you want to get numbers at any depth then you can flat at any level
// using Infinity as
// return arr.flat(Infinity).reduce((acc, curr) => acc * curr, 1);
}
console.log(multiplyAll([[1], [2], [3]]));
Well, it looks like you have multiple issues, two of them are already as following:
In line 2 you wrote once Let with a big letter at the beginning.
Your second array needs an {} otherwise it will error out
Can you please explain to me j*= product? Can you maybe include a few examples of how you would call this Code and what kind of response you would get? depending on that I will create you a Clear answer!

How can I add the numbers in the following code?

I have an array named arr = [[1,2],4] , and for loops to access the numbers. But I can't seem to add the last number. Why is it not working?
let arr = [[1,2],4];
let total = 0;
for(let i = 0; i < arr.length; i++) {
for(let j = 0; j < arr[i].length; j++) {
total += arr[i][j];
}
}
console.log(arr.length) // returns length = 2
console.log(total); // returns total = 3
Your issue is that your array doesn't just consist of only arrays, it consists of both single numbers and nested arrays. As a result, your inner loop won't be able to loop over the number 4 as it is not an array (and so it won't have a .length property).
let arr = [[1,2],4];
// no issues-^ ^-- no `.length` property (inner for loop won't run)
For a problem like this, you can make use of a recursive function, which when you encounter a nested array, you can recall your function to perform the addition for that array.
See example below (and code comments):
function sumNums(arr) {
let total = 0;
for (let i = 0; i < arr.length; i++) {
if(Array.isArray(arr[i])) { // If current element (arr[i]) is an array, then call the sumNums function to sum it
total += sumNums(arr[i]);
} else {
total += arr[i]; // If it is not an array, then add the current number to the total
}
}
return total;
}
let arr = [[1,2],4];
console.log(sumNums(arr)); // 7
You can also make use of a recursive call with .reduce() if you would like to take that approach:
const arr = [[1,2],4];
const result = arr.reduce(function sum(acc, v) {
return acc + (Array.isArray(v) ? v.reduce(sum, 0) : v);
}, 0);
console.log(result); // 7
Since the values can be array or numbers, Just add the check before doing the inner loop
if (!Array.isArray(arr[i])) {
total += arr[i];
continue;
}
let arr = [[1,2],4];
let total = 0;
for(let i = 0; i < arr.length; i++) {
if (!Array.isArray(arr[i])) {
total += arr[i];
continue;
}
for(let j = 0; j < arr[i].length; j++) {
total += arr[i][j];
}
}
console.log(arr.length) // returns length = 2
console.log(total);

Sort an array of strings based on a character in the string

I am trying to sort an array of strings based on a character inside each of those strings. So far, I have this
function doMath(s) {
let arr = s.split(' ');
let letterArr = [];
let sortedArr = [];
let n = 0;
for (var i = 0; i < arr.length; i++) {
n = arr[i].indexOf(arr[i].match(/[a-z]/i));
letterArr.push(arr[i][n]);
}
letterArr.sort();
console.log(letterArr);
for (i = 0; i < arr.length; i++) {
for (var j = 0; j <= arr[i].length; j++) {
if (arr[i].indexOf(letterArr[j]) > -1) {
sortedArr.unshift(arr[i]);
}
}
}
console.log(sortedArr);
}
doMath("24z6 1x23 y369 89a 900b");
The problem is shown when I log this array. If I use sortedArr.push(arr[i]);,
then the output is:
["24z6", "1x23", "y369", "89a", "900b"]
However, when I use sortedArr.unshift(arr[i]);, I get the output:
["900b", "89a", "y369", "1x23", "24z6"]
I am not sure why the b comes before the a.
I just want it to be a-z for the sorting. I tried push() and it is correct but backwards (z-a). When I try unshift(), it's correct except the b and a are switched.
function doMath(s) {
return s.split(' ').sort(function (a,b) {
return a.match(/[a-z]/i)[0].localeCompare(b.match(/[a-z]/i)[0])})
}
console.log(doMath("24z6 1x23 y369 89a 900b"));

Categories

Resources