I’ve been doing a lot of picking random objects from an array in my latest project but occasionally same the object is picked again which is not ideal.
what is the best method of doing this so that it wont pick the same object again? This is an example of the code im using:
void ChangeMusic()
{
int m = Random.Range(0, musics.Length); // Pick a random song
MusicManager.play(musics[m], 1f, 1f); // Play it
Invoke("changeMusic", musics[m].length-1f);// Recall this function later. -1f for the fade out duration
}
Perhaps you could store the random number that’s chosen from the array into a temp variable and each time you go to pick a new number from the array you can compare the picked number to the stored number and loop until the two numbers are not the same, then overwrite the temp variable with the newly picked number.
If you must use arrays, you could do something annoying but effective such as storing how many times you’ve picked from the array, and sorting the array so that picked things are at the beginning of the array, and unpicked things are at the end, as just an example solution.
So let’s say you have picked 2 songs so far, each time it should have sorted the array so that the 2 songs are now in index 0 and 1. Then you know to pick your next random number between 2 and the length of the array, because you should also have stored that 2 songs have been picked.
Another solution would be to completely replace the array each time a song is picked with a new array containing everything but the picked song. Eventually your array would have one thing in it. In this case, play that song, then replace it with an array containing everything again (I’m assuming this is for a music playlist of sorts)
Using List(T) from System.Collection.Generic seems a lot better, though. They have dynamic size and a lot of methods to remove and add members easily.
You could easily just choose a random number between 0 and List.Count, then set that song to play, then use List.RemoveAt to pop it from the list. You could keep a separate list or array as a “master” which wouldn’t have the songs removed, so when your playing List no longer had members, you could just repopulate it with the master list. An array would be easy to populate from the inspector, then you could just have a method that resets the list to the full list of songs and call that on Awake and whenever you need.
Yeah, I was thinking of this earlier today and realized it would probably just be better to shuffle it once and then repeat the shuffled list (so you don’t risk the last song being the same as the first song on the second play), which is a lot easier to do – what BC said. I’ve been doing a LOT with Lists recently and way overcomplicated it hahaha.