How does a mutable array works in js? - javascript

i'm Learning Javascript from multiple ressources like FCC where i can't Understand one concept with the mutable arrays. I've got an example :
var myArray = [1,2,3];
myArray[0]=3; //[3,2,3]
var ourArray = [1,2,3];
ourArray[1] = 3; //[1,3,3]
i can't get how the [3,2,3] and [1,3,3] are created.
thanks for your help
ok, got it but what if my code looks like this :
var arr = [ [1,2,3], [4,5,6], [7,8,9], [[10,11,12], 13, 14] ];
arr[3]; // equals [[10,11,12], 13, 14] arr[3][0]; // equals [10,11,12]
arr[3][0][1]; // equals 11 how the arr[3] or arr[3][0] work ?

Arrays in JS starts with 0 index.
In the first case you're replacing 1 with 3
[1, 2, 3]
^
3
[0, 1, 2] <- indexes
In the second case, you're replacing 2 with 3
[1, 2, 3]
^
3
[0, 1, 2] <- indexes

Mutable just means that each element in the array can be changed.
The number inside the brackets is the order starting with 0;
So originally myArray[0] is 1, myArray[1] is 2, myArray[2] is 3
When you do myArray[0] = 3 it sets the value in the first spot to 3, hence getting 3,2,3

When you are writing myArray[0]=3 here you are setting a value of a particular position in that array same with ourArray[1] so you are making changes in that array with the new values so the console gives you array with new values like in your example you defined with the name myArray and ourArray .

Let me go through your code line by line,
var myArray = [1,2,3];
creates a myArray with [1, 2, 3]
myArray[0]=3;
index 0 of myArray is set to 3;
so myarray holds [3, 2, 3]
var ourArray = [1,2,3];
ourArray is created with [1, 2, 3]
ourArray[1] = 3;
index 1 of our array is set to 3;
so our array holds [1, 3, 3]
Please note that index starts with 0 and not with 1.

Related

Why reducing the length of an array makes last element undefined but the length doesn't change?

Hello I'm new to javascript.
I was trying to reduce the length of an array by 1.
I did this, the last element is undefined now, but the length is still 5.
var arr = [1, 2, 3, 4, 5];
arr.length = arr.length--;
console.log(arr);
console.log(arr.length);
I'm confused. Instead of [1, 2, 3, 4] or [1, 2, 3, 4, 5]. Why it gives me [1, 2, 3, 4, undefined]?
Can someone explain? Thanks
arr.length-- will reduce the length by 1 already but will return the previous length, meaning you're reducing the array's length by 1 and then immediately assigning the previous length to arr.length, meaning you're changing it back to a five element array (but you already removed the fifth element ,so that's now undefined.
If you want to just reduce the array's length, you can user arr.length--; alone.
var arr = [1, 2, 3, 4, 5];
arr.length--;
console.log(arr);
console.log(arr.length);
You need to use array.prototype.pop you instead to reduce the size of your array:
var arr = [1, 2, 3, 4, 5];
arr.pop();
console.log(arr);
console.log(arr.length);
Take into consideration that arr.length-- with a length of 0 causes an error.
A timeline of what's happening in array.length = array.length--:
The -- operator changes array.length from 5 to 4.
array.length-- evaluates to the previous value of array.length, which is 5
This value is assigned to array.length, changing it from 4 to 5.
So you are shrinking the array and then growing it.
My advice: avoid mutating your arrays and instead use slice:
var arr = [1, 2, 3, 4, 5];
var newArr = arr.slice(0, -1);
console.log(newArr);
console.log(newArr.length);
If you insist on mutating your arrays, then I suggest you use a less mystifying operator: -=:
var arr = [1, 2, 3, 4, 5];
arr.length -= 1;
console.log(arr);
console.log(arr.length);
var arr = [1, 2, 3, 4, 5];
arr.splice(arr.length-1);
console.log(arr); //[1,2,3,4] --Expected Log
console.log(arr.length); //4 --Expected Log
Or you can try this:
var arr = [1, 2, 3, 4, 5];
arr.pop();
console.log(arr); //[1,2,3,4] --Expected Log
console.log(arr.length); //4 --Expected Log
if you want reduce , you can use 'splice'

Swapping array values with destructuring assignment and indexOf()

I'm trying to swap the two lowest values in a shuffled array containing the numbers 0-14. For those curious, I'm implementing the shuffling algorithm for a 15 puzzle described by pkpnd here.
I wanted to try destructuring assignment, as described here, but am encountering an unexpected behavior. I realize that I can get my code working (and make it more readable) by just creating a temporary variable, but I'd like to understand what's happening before moving on.
I'm grabbing a subset of my array [1,2] and then trying to replace it with [2,1]. For some reason, it's only swapping the values when their order in the original array is opposite of the order of my subset.
I originally tried this:
var arr1 = [1, 2, 3, 4];
var arr2 = [2, 1, 3, 4];
[arr1[arr1.indexOf(1)], arr1[arr1.indexOf(2)]] = [arr1[arr1.indexOf(2)], arr1[arr1.indexOf(1)]];
[arr2[arr2.indexOf(1)], arr2[arr2.indexOf(2)]] = [arr2[arr2.indexOf(2)], arr2[arr2.indexOf(1)]];
console.log("arr1: " + arr1, "\narr2: " + arr2);
And then tried this:
var arr1 = [1, 2, 3, 4];
var arr2 = [2, 1, 3, 4];
[arr1[arr1.indexOf(1)], arr1[arr1.indexOf(2)]] = [2, 1];
[arr2[arr2.indexOf(1)], arr2[arr2.indexOf(2)]] = [2, 1];
console.log("arr1: " + arr1, "\narr2: " + arr2);
But both produce identical output:
arr1: 1,2,3,4
arr2: 1,2,3,4
I would expect that the position of 1 and 2 would be swapped for both arrays, but they're only swapped in arr2. I suspect this has to do with they way the initial array subset [1,2] is created, but I'm not sure.
Can anybody explain why the values aren't always swapped?
The result is simple, because it goes step for step for each item of destructuring assingment. And while the values are changing, the index of the values changes.
Case 1 [1, 2, 3, 4]
Get index of target for the first value 2
[arr1[arr1.indexOf(1)], arr1[arr1.indexOf(2)]] = [2, 1];
// ^^^^^^^^^^^^^^^ 0
Assign 2 to arr1[0]
[2, 2, 3, 4]
Get index of target for the second value 1:
[arr1[arr1.indexOf(1)], arr1[arr1.indexOf(2)]] = [2, 1];
// ^^^^^^^^^^^^^^^ 0
Assign 1 to arr1[0]
[1, 2, 3, 4]
Case 2 [2, 1, 3, 4]
Get index of target for the first value 2
[arr2[arr2.indexOf(1)], arr2[arr2.indexOf(2)]] = [2, 1];
// ^^^^^^^^^^^^^^^ 1
Assign 2 to arr1[1]
[2, 2, 3, 4]
Get index of target for the second value 1:
[arr2[arr2.indexOf(1)], arr2[arr2.indexOf(2)]] = [2, 1];
// ^^^^^^^^^^^^^^^ 0
Assign 1 to arr1[0]
[1, 2, 3, 4]

Javascript array is syncing with another assigned array

I've been racking my brain trying to figure out why these arrays are syncing after I assign one to the other. The output should be "1, 2, 3, 4" but instead it's "5, 6, 7, 8". Do I need to copy the arrays differently?
var firstArray = [1, 2, 3, 4];
var secondArray = [5, 6, 7, 8];
for (i = 0; i < firstArray.length; i++) {
var myTempArray = firstArray;
myTempArray[i] = secondArray[i];
}
console.log("Result: " + firstArray);
Expected output:
Result: 1,2,3,4
Actual output:
Result: 5,6,7,8
How do I alter the second array without changing the first array?
Arrays are mutable objects. So they just contain references. You need to "copy" an array in order to make a copy, not just assign like primitive objects. To copy an array, there are various methods. One best method is:
myTempArray = firstArray.slice();
What you are doing is a shallow copy:
Also, another big issue is that, you have the array assignment inside the loop, which keeps the myTempArray changing. You need to take it out of the loop. Your final code should look like:
var firstArray = [1, 2, 3, 4];
var secondArray = [5, 6, 7, 8];
var myTempArray = firstArray.slice();
for (i = 0; i < firstArray.length; i++) {
myTempArray[i] = secondArray[i];
}
console.log("Result: " + firstArray);

while(i--) loop in javascript

I normally use while loop as:
while (i<some_value)
I saw while(i--) syntax and thought it is shorter and cooler and tried the following in google-chrome.
var num_arr= [4,8,7,1,3];
var length_of_num_arr=num_arr.length;
while(length_of_num_arr--) console.log(num_arr);
[4, 8, 7, 1, 3]
[4, 8, 7, 1, 3]
[4, 8, 7, 1, 3]
[4, 8, 7, 1, 3]
[4, 8, 7, 1, 3] **// THIS IS EXPECTED RESULT**
But When I try...
while((num_arr.length)--) console.log(num_arr);
[4, 8, 7, 1]
[4, 8, 7]
[4, 8]
[4]
[] // WHY IS THIS HAPPENING??
Is there some hidden things you need to understand to use this syntax?
Arrays’ length property is writable, and will cut off their elements or add empty slots as appropriate when you set it.
var items = [1, 2, 3, 4, 5];
items.length = 3; // items is now [1, 2, 3]
items.length = 6; // items is now a sparse array: [1, 2, 3, undefined × 3]
So, don’t do that.
When you do array.length-- you're potentially shortening the array by one element each time.
See the reference under the section Shortening the array from: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/length
Array.prototype.length can be re-written programmatically and it potentially shorten your array by the new length you assign.
For example
a = [1,2,3,4,5,6,7,8,9,10];
// Shorten the array by one element
a.length--; // a <-- [1,2,3,4,5,6,7,8,9]
// In case you want to shorten your array to 3 elements, you can:
a.length = 3; // a <-- [1,2,3]
When you set the length property of an array to a lower value, the items at the end are removed:
var arr = [1,2,3,4,5];
arr.length; // 5
arr.length = 3;
arr; // [1,2,3]
This is described in the spec:
While newLen < oldLen repeat,
Set oldLen to oldLen – 1.
Let deleteSucceeded be the result of calling the [[Delete]] internal method of A passing ToString(oldLen) and false
as arguments.
In your code you use the postfix decrement operator (--) which reduces the length of the array.

javascript splice - strange issue

I wonder what's wrong with this
$(function() {
var arr1=new Array('A','B','C','D','E','F','G');
var arr2=new Array('F','D','B');
var arr3=arr1;
for(x=0; x<arr3.length; x++) {
if(jQuery.inArray(arr3[x],arr2) == -1) {arr3.splice(x, 1);}
}
alert(arr1.join(','));
alert(arr3.join(','));
});
I thought arr1 should still be Array('A','B','C','D','E','F','G'), but after this operation, arr1 becomes arr3. It doesn't make sense to me since the entire operation doesn't touch arr1 at all.
Found the answer after posting this. See duplicating arrays javascript splicing
Assignment like var arr3=arr1; are done by reference i.e. arr3 variable now points to same location where arr1 variable points to. The underlined data (in this case array) is the same. Essentially arr1 and arr3 are same. So any change done via one is visible via other. If you want to duplicate the array of simple types use slice(0)
var arr3 = arr1.slice(0);
var x = [3, 4, 5]
var y = [3, 4, 5]
var z = y
x === y // false
y === z // true (y and z reference the same object)
y.push(6)
y // [3, 4, 5, 6]
z // [3, 4, 5, 6]
var x2 = x.slice(0)
x2 === x // false
x2.push('foo')
x2 // [3, 4, 5, 'foo']
x // [3, 4, 5]
Use Array.prototype.slice to copy an array.
arr1 is a Array Object. when you copy arr1 like var arr3 = arr1, we just get a new reference to the original object.
so , when you change the arr3 , arr1 also change.
you should search "how to clone a object", this may help you.

Categories