25. Random groups

This is slightly more complicated than it might initially appear, largely due to the requirement that we leave the original array or list unmodified. If it weren't for that requirement, you could simply randomize the array or list and then return the required number of items from the randomized values.

That won't work in this case, but it does suggest a simple workaround. Copy the original array or list, randomize the copy, and return the desired number of items. If the items are small, such as integers or references to objects, then that would be reasonable. However, if the items are large, such as large structures, then that would use a lot of memory.

The approach that I use is to make an array of indices. You can then randomize the indices and use them to pick the values to return. The following method demonstrates that approach:

// Pick the indicated number of random items.
public static T[] ChooseGroup<T>(this T[] values, int number)
{
// Make an array holding indices 0, 1, 2, ..., numValues - 1.
int numItems = values.Length;
int[] indices = Enumerable.Range(0, numItems).ToArray();

// Partly randomize the indices array.
if (number > numItems) number = numItems;
for (int i = 0; i < number; i++)
{
// Pick a later item to swap into position i.
int j = Rand.Next(i, numItems);

// Swap items i and j.
int temp = indices[i];
indices[i] = indices[j];
indices[j] = temp;
}

// Build the result array.
T[] results = new T[number];
for (int i = 0; i < number; i++) results[i] = values[indices[i]];
return results;
}

The method gets the number of items in the array and then uses Enumerable.Range to make an array holding the values 0, 1, 2, and so on up to the array's last index.

The method then uses code similar to the code used by Solution 51, Randomize items, to randomize the beginning of the array of vertices. You could simply call the index array's Randomize extension method, but we don't need to randomize the entire array. This code only randomizes enough indices to return the desired number of items.

Next, the code creates a results array. It loops through the desired number of items, uses the corresponding indices to find the randomly selected items, and inserts them into the new array. When it has filled the results array, the method returns it.

The code to choose a group of random items from a list is very similar. The main difference is that you need to use the list's Count property to determine the number of items in the list.

In the example solution, I also made the list version of the method return a list of items instead of an array of items, mostly to show how you could do that.

Download the RandomGroups example solution to see additional details.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
3.149.253.239