0

I Need to render a table to the HTML with 16 cells containing numbers from 1 to 16 in a random order, the question said that you should pop a number from the array and i cant figure it out how to do it, tnx for the help :)

here is my code

"use strict";

let numArr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16];
let shuffled = shuffleArr(numArr);

function shuffleArr(arr) {
  for (let i = arr.length - 1; i > 0; i--) {
    const j = Math.floor(Math.random() * (i + 1));
    const temp = arr[i];
    arr[i] = arr[j];
    arr[j] = temp;
  }
  console.log(arr);
  return arr;
}

function renderTable(arr) {
  let strHTML = "";
  for (let i = 0; i < arr.length / 2; i++) {
    strHTML += "<tr>";
    for (let j = 0; j < arr.length / 2; j++) {
      strHTML += `<td></td>`;
    }
    strHTML += "</tr>";
  }

  let elTable = document.querySelector(".board");
  elTable.innerHTML = strHTML;
}
JohnnyNice
  • 13
  • 2
  • pop as in the array method `array.pop`? That's a really inefficient way of selecting a random element from an array as you have to make a new version of the array for every iteration. `array.slice` would be much better to remove random elements once chosen and put into a table cell. Must you use `array.pop`? Also, do you have to meet a specified number of rows/cols in your table? – Dave Pritlove Mar 17 '22 at 20:00
  • `pop` is a must? And what dimensions for table? – Dave Pritlove Mar 17 '22 at 20:34
  • yes i need to use the pop method 2D table – JohnnyNice Mar 17 '22 at 20:37
  • thats the question, i have tried to solve this for almost 3 hours... ||| User sees a board with 16 cells, containing numbers 1..16, in a random order o Hint: use an HTML table o Hint: Nice technique for building the board: place the 16 numbers in a simple array, shuffle it, then build the by popping a number from the nums array. o Note: there is no need to use as matrix in this exercise
    – JohnnyNice Mar 17 '22 at 20:40
  • Choosing a random number from an array by shuffling it and removing the last element with `pop` is about the most computationally expensive way it could be done. So, I assume whoever set you the problem wants you to learn about array randomising algorithms. You might start here: https://stackoverflow.com/questions/2450954/how-to-randomize-shuffle-a-javascript-array. Good luck. (doesn't matter to me now, but you still didn't answer what dimensions your table is, 2d could be 2x8, 4x4, or 8,2. If it's important you should specify) – Dave Pritlove Mar 17 '22 at 20:42
  • @JohnnyNice ok, my last comment was being written before I saw your last reply. If I had that question, I would ignore the hints and use the simpler method of choosing a random element. I'll post a working example (it doesn't use pop so will not help you if you're set on using pop) but it does make a random table. – Dave Pritlove Mar 17 '22 at 20:48
  • thank you so much, i didnt understood what you meant by dimensions, now i do it needs to be 4x4, and then i have to add difficulties (larger boards: 25 cells, 36 cells) – JohnnyNice Mar 17 '22 at 20:50
  • in my example, if you need larger 'boards' you simply set the `rows` and `columns` variables accordingly (and, of course, make sure your array has enough numbers to fill it. If your board is always square, you could set rows and cols programmatically as `rows = cols = Math.sqrt(numArr.length)` -providing the length of the array is a perfect square (16,25,36,49 etc). – Dave Pritlove Mar 17 '22 at 21:01
  • @DavePritlove sorry, but i didnot fully understood how i can programmatically change the size of row and columns – JohnnyNice Mar 18 '22 at 11:06
  • replace the `let cols=4` and `let rows=4` with ` let cols=rows=Math.sqrt(numArr.length);`. That will take the square root of the number of elements you have and set both rows and cols to that value. Yes, you can use two equal signs as they are `assignment` operators not equalities. If your array's length is not a square number (4,9,16,25,36, etc) long it will throw an error so be careful. – Dave Pritlove Mar 18 '22 at 13:19

1 Answers1

0

This method achieves the end goal but does not use array.pop (which would require the complexity of a random shuffle on the array (see How to randomize (shuffle) a JavaScript array?)

It simply iterates through a nested loop for each row and column, choosing a random element each time, with that element being removed once used. Note, array.length as a mulitplier for the random number (range 0-1) takes care of the random index always been in range for the shortening array.

let numArr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16];

let rows=4;
let cols=4;

let markup = "";
let randomIndex = 0;

for (let row=0; row<rows; row++) {
  markup += "<tr>"
  for (let col=0; col<cols; col++) {
   randomIndex = Math.floor(Math.random()*numArr.length);
   markup += `<td>${numArr[randomIndex]}</td>`;
   numArr.splice(randomIndex, 1); // removed used value;  
  } // next col;
  markup += "</tr>";
} // next row; 

const table = document.createElement('table');
table.innerHTML = markup;

document.body.appendChild(table);
table, td {
  border: 1px solid black;
  font-family: monospace;
  text-align: right;
}

table {
  border-collapse: collapse;
}

td {
  width: 2em;
}
Dave Pritlove
  • 2,601
  • 3
  • 15
  • 14
  • thank you so much ! i almost punched my computer with that question – JohnnyNice Mar 17 '22 at 21:01
  • great. Ask if there's any bits you don't get. I used a template literal to write the cell `${numArr[randomIndex]}` (very useful when assembling markup in js, but is equivalent to "" + numArr[randomIndex] + ""). – Dave Pritlove Mar 17 '22 at 21:06
  • no, i now get it, you made everything clear, thank you very much – JohnnyNice Mar 17 '22 at 21:08
  • lol, now i have to deal that the user should click the buttons in a sequence (1,2,3 etc...) and if its right the button changes color, but i think i could handle this – JohnnyNice Mar 17 '22 at 21:10
  • If you have to post future questions, take time to think through and explain your problem as fully as possible, with examples of what approach you've tried and where problems were found. Follow the tips here: https://stackoverflow.com/help/how-to-ask for the best results. Also, don't forget to accept an answer (by clicking the tick next to it) if it solved your problem better than any others. It's ok to wait a little in case better solutions come along but accept one when you are satified. Good luck – Dave Pritlove Mar 17 '22 at 21:24