javascriptarraysfunctionfor-looprandom

JavaScript generating always the same numbers on the second for loop


The script:

let col1 = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15] 
let col2 = [16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30]
for(let i = 0; i < 5; i++) {
    const random = Math.floor(Math.random() * col1.length + 1)
    const index = col1.indexOf(random)
    const number = col1.at(index)
    col1.splice(index, 1)
    console.log(number)
}
for(let i = 0; i < 5; i++) {
    const random = Math.floor(Math.random() * col2.length + 1)
    const index = col2.indexOf(random)
    const number = col2.at(index)
    col2.splice(index, 1)
    console.log(number)
}

The first for loop always generates 5 random numbers from the first array. But the second for loop always shows the same results (30, 29, 28, 27, 26). What's causing this behavior?


Solution

  • const random = Math.floor(Math.random() * col2.length + 1);
    

    generates a random integer between 0 and 15, since col2.length is 15. Then,

    const index = col2.indexOf(random);
    

    always returns -1, since there isn't any element with value random in col2. So then

    const number = col2.at(index);
    

    assigns always col2's last item to number, which changes each iteration since

    col2.splice(index, 1);
    

    removes col2's last element.

    If you want five different elements from each array, you can just do:

    let col1 = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15] 
    let col2 = [16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30]
    
    for(let i = 0; i < 5; i++) {
        const index = Math.floor(Math.random() * col1.length);
        const number = col1.at(index);
        col1.splice(index, 1);
        console.log(number);
    }
    for(let i = 0; i < 5; i++) {
        const index = Math.floor(Math.random() * col2.length);
        const number = col2.at(index);
        col2.splice(index, 1);
        console.log(number);
    }

    EDIT: removed the +1 in Math.floor() to stay within range.