1

I have two pieces of code I wrote, I suppose they should work the same. As you may notice the only thing which is different between the two is the declaration of the for-loop.

Why is the code with for-in not working as expected?

Thanks in advance.

const allPermutations1 = s => {
     let permutations = []

     const recursion = (s, p = '') => {

         if (s.length === 0) return permutations.push(p)

         for (let i = 0; i < s.length; i++)
             recursion(s.slice(0, i) + s.slice(i+1), p + s[i]) 
     }

     return (recursion(s), permutations)
 }

allPermutations1('123') // ["123", "132", "213", "231", "312", "321"]

const allPermutations2 = s => {
    let permutations = []

    const recursion = (s, p = '') => {

        if (s.length === 0) return permutations.push(p)

        for (let i in s)
            recursion(s.slice(0, i) + s.slice(i+1), p + s[i]) 
    }

    return (recursion(s), permutations)
}

allPermutations2('123') // ["123", "132", "21", "312", "321"]
Fredo Corleone
  • 544
  • 1
  • 6
  • 16
  • read here https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/for...in – Code Maniac Dec 24 '18 at 18:41
  • 2
    REsearch the difference between `for in` and `for of` loops... The former is for iterating over objects, not arrays... – SakoBu Dec 24 '18 at 18:48
  • Closely related: [Why is using `for…in` on arrays such a bad idea?](https://stackoverflow.com/q/500504/1048572) – Bergi Dec 24 '18 at 20:06
  • Possible duplicate of [Why is using "for...in" with array iteration a bad idea?](https://stackoverflow.com/questions/500504/why-is-using-for-in-with-array-iteration-a-bad-idea) – Ian Kemp Dec 24 '18 at 22:13

2 Answers2

3

A for...in loop iterates over keys and returns a string. When you apply the i+1 iterator inside the splice, you are returning a string concatenation instead of incrementing the value. E.g '1' + '2' is '12' instead of 3. This situation may cause problems when splicing the numbers properly. You need to parse the key to a number for performing the operation as expected.

1
const allPermutations2 = s => {
    let permutations = [];

    const recursion = (s, p = "") => {
        if (s.length === 0) return permutations.push(p);

        for (let i in s) {
            recursion(
                s.slice(0, parseInt(i)) + s.slice(parseInt(i) + 1),
                p + s[parseInt(i)]
            );
        }
    };
    return recursion(s), permutations;
};

Will produce the same result as the first one. when you do for..in the keys are strings.

Countingstuff
  • 733
  • 5
  • 14