3

I’ve been playing with random array arrangements and was wondering if there is a way to pull word from the array only once. So every time you click on the changeWorld button then it will randomly draw from the array list until all the words where used only once?

Learning JavaScript so I don't need anyone to write me the code, just want get pushed in the right direction and know if it is possable. There isn't anything I can find that address the concept.

<body>

<button id="change-world-btn">Change World</button>

Hello <span class="world-name">World!</span><br />



<script type="text/javascript">

var worlds = new Array ("Pluto", "Mars", "Saturn", "Jupiter", "Uranus");

function newWorld() {
    return worlds[Math.floor(Math.random() * worlds.length)];
}

elements = document.getElementsByTagName('span');

document.getElementById('change-world-btn').onclick = function() {
    world = newWorld();
    for(var i = 0, el; el = elements[i++];) {
        if(el.className == 'world-name') {
            el.innerHTML = world;
        }
    }
};
</script>       
</body>
3
  • It's definitely possible, but I don't see anything wrong with your code. Are having problems? Do you want refactoring advice? Commented Aug 13, 2012 at 19:02
  • @Linuxios: The code picks words by random, but there is nothing that keeps words from being repeated. Commented Aug 13, 2012 at 19:04
  • 1
    randomizing the whole array and then picking from the end of the array is better. Here is an example jsfiddle.net/4zEuh (if you are curious why from the tail, it is because if you remove from the beginning, the whole array moves every item to the left every time) Commented Aug 13, 2012 at 21:27

7 Answers 7

6

Remove the words that you have used from the array:

function newWorld() {
  var index = Math.floor(Math.random() * worlds.length);
  var world = worlds[index];
  worlds.splice(index, 1);
  return world;
}

You might also want to check if the array is empty first.

Sign up to request clarification or add additional context in comments.

4 Comments

Note that splice returns an array not just the element.
@AndreasKöberle: Note that the code doesn't use the return value of the splice call.
just God knows what is going on behind the doors... I mean, if you remove one element from the array in the middle, the other elements must reorganize every time. I prefer more the "a)randomize b)pop last" approach.
@ajax333221: There is user interaction between each pick, so it's not run in a tight loop. You would need a really huge array before it would even be possible to notice any difference.
4

This sounds like a job for a stack or a queue. You can take your array, shuffle to get your "randomness", push each element from your array into a stack or queue, then pop off an element everytime the user clicks your button. Edit: Here is a small example of a stack.

var stack=new Array();
stack.push("A");
stack.push("B");
stack.push("C");
alert(stack.pop());
alert(stack.pop());
alert(stack.pop());

1 Comment

+1 this is the best approach, but it deserves a better example.
1

This worked very well, and there is a return phrase when the array is used up.

thanks for all the help.

<button id="change-world-btn">Change World</button>

Hello <span class="world-name">World!</span><br />



<script type="text/javascript">
   var worlds = new Array ("Pluto", "Mars", "Saturn", "Jupiter", "Uranus");

function newWorld() { 
var index = Math.floor(Math.random() * worlds.length); 
var world = worlds[index]; 
worlds.splice(index, 1); 
return world; 
} 


elements = document.getElementsByTagName('span');

document.getElementById('change-world-btn').onclick = function() {
    world = newWorld();
    if(worlds==""){ world="no more worlds"}
    for(var i = 0, el; el = elements[i++];) {
        if(el.className == 'world-name') {
            el.innerHTML = world;
        }
    }
};
    </script>       


</body>

1 Comment

Comparing an array to a string might actually work, but it's not easy to see why. Check the length instead: if (worlds.length == 0).
0

You could delete the word from the array using splice:

function newWorld() {
    var i = Math.floor(Math.random() * worlds.length)
    return worlds.splice(i , 1)[0];
}

Comments

0

Try the splice method of array.

Demo at http://jsfiddle.net/WKEC2/1/

Comments

0

This kind of thing like document.getElementById('change-world-btn').onclick dont exist. You have do some like And in you javascript something like:

function getNewName(){
document.getElementById('yourelementid').innerHtml = newWorld();
}

if you want to do it with all elements try something like that:

document.getElementById('change-world-btn').onclick = function() {
world = newWorld();
for(var i = 0, i < elements.lenght; el = elements[i++];) {
    if(el.className == 'world-name') {
        el.innerHTML = world;
    }
}

Comments

0

Alternatively, you can randomly sort the array, and then simply cycle through it:

// Math.random() returns a number between 0-1
// Math.round() rounds the number to either 0 or 1
// Subtracting 0.5 results in either +.5 or -.5
function randomSort(){
    return (Math.round(Math.random())-0.5);
}


var elements = document.getElementsByTagName('span');  
var worlds = new Array ("Pluto", "Mars", "Saturn", "Jupiter", "Uranus");

// sort the array
worlds.sort(randomSort);

document.getElementById('change-world-btn').onclick = function() {
    world = worlds.shift();
    //worlds.push(world); - add this line if you want to cycle the array indefinitely
    if(!world) { // check to make sure world exists
        alert('No more worlds!');
    } else {
        for(var i = 0, el; el = elements[i++];) {
            if(el.className == 'world-name') {
                el.innerHTML = world;
            }
        }
    }
};

jsFiddle DEMO

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.