-1

Why reverse() doesn't work if my array have elements with string as a key.

var myArray = [];
myArray["test"] = 100;
myArray["test2"] = 200;

console.log(myArray)
console.log(myArray.reverse())

Both returns the same result.

How can I change it to make it work?

DEMO: https://www.w3schools.com/code/tryit.asp?filename=GG4PXCHZ4VUD

DiPix
  • 4,140
  • 9
  • 47
  • 83

3 Answers3

1

.reverse() is a function of arrays, where elements are indexed by their position. Your code is not adding elements to the array, but rather adding properties on the array object. This works and the properties can be accessed, but reversing does nothing as these are not elements. The array is still of 0 length.

You will have to either:

  1. Make myArray an object of a different type. In this case, reverse will still not work, and you will have to write code to sort manually. Other answers have provided some guidance as to how to achieve this
  2. Add your elements to the array using push() or numeric indices, in which case you'll lose the string indices but can use array sorting methods such as .reverse()

While numbers have an intrinsic ordering, object property keys follow different rules. If you want to reverse a string-indexed object, consider writing a function to insert objects to a new Map in reverse order.

MLarionov
  • 513
  • 5
  • 19
0

Since you do not actually need any array methods, it would be better to simply use an object instead.

You can create a new reversed array by looping over Object.keys() backwards. See the code in action here.

var myArray = [];
myArray["test"] = 100;
myArray["test2"] = 200;
function reverseAssociative(arr){
  const keys = Object.keys(arr);
  const res = [];
  for(let i = keys.length - 1; i >= 0; i--){
    res[keys[i]] = arr[keys[i]];
  }
  return res;
}
const res = reverseAssociative(myArray);
for(const key in res){
  console.log(key, res[key]);
}

You can simplify it by using reduce on Object.entries after reversing. See the code in action here.

myArray = Object.entries(myArray).reverse().reduce((acc,[key,val])=>(acc[key]=val,acc),[])
iota
  • 34,586
  • 7
  • 32
  • 51
  • Looks kinda complicated. No way to simplify it somehow? – DiPix Jun 24 '20 at 15:58
  • 1
    Using property access on an array is not good practice, consider using another type – MLarionov Jun 24 '20 at 16:11
  • @MLarionov Yes, the array should be an object. – iota Jun 24 '20 at 16:13
  • Weird http://prntscr.com/t5qqlu it looks like that only keys changed position, but under the preview everything looks like the same – DiPix Jun 24 '20 at 16:23
  • @DiPix Did you try logging `Object.entries` of the array? How it's displayed in the console may vary. If it is still in the wrong order, consider changing the associative array to an object (`{}`). – iota Jun 24 '20 at 16:23
0

Arrays values are only accessible by index.

myArray[0] = 100;

myArray[1] = 200;

console.log(myArray) // [100, 200]

console.log(myArray.reverse()) // [200, 100]

You can store values by keys in objects.

var myObject = {};
myObject["test"] = 100;
myObject["test2"] = 200;

console.log(myObject) // {test: 100, test2: 200}

That said, you can reverse an object by doing this:

Object.entries(myObject).reverse().reduce((a, b) => {
 a[b[0]] = b[1];
 return a
},{})
Akin Aguda
  • 334
  • 3
  • 10