Skip to content

Commit

Permalink
Add Random.Shuffle() (#192)
Browse files Browse the repository at this point in the history
  • Loading branch information
SimonCropp authored Jul 1, 2024
1 parent d99166a commit 6c1b1ff
Show file tree
Hide file tree
Showing 5 changed files with 99 additions and 12 deletions.
2 changes: 1 addition & 1 deletion apiCount.include.md
Original file line number Diff line number Diff line change
@@ -1 +1 @@
**API count: 297**
**API count: 299**
2 changes: 2 additions & 0 deletions api_list.include.md
Original file line number Diff line number Diff line change
Expand Up @@ -196,6 +196,8 @@
#### Random

* `Void NextBytes(Span<Byte>)` [reference](https://learn.microsoft.com/en-us/dotnet/api/system.random.nextbytes#system-random-nextbytes(system-span((system-byte))))
* `Void Shuffle<T>(T[])` [reference](https://learn.microsoft.com/en-us/dotnet/api/system.random.nextbytes#system-random-nextbytes(system-span((system-byte))))
* `Void Shuffle<T>(Span<T>)` [reference](https://learn.microsoft.com/en-us/dotnet/api/system.random.nextbytes#system-random-nextbytes(system-span((system-byte))))


#### ReadOnlySpan<Char>
Expand Down
20 changes: 15 additions & 5 deletions src/Consume/Consume.cs
Original file line number Diff line number Diff line change
Expand Up @@ -460,16 +460,26 @@ void GetMemberWithSameMetadataDefinitionAs(MemberInfo info)
#if FeatureMemory
void RandomNextBytesSpan()
{
// Create a new instance of Random
var random = new Random();

// Create a span of bytes
Span<byte> buffer = new byte[10];

// Fill the span with random bytes
random.NextBytes(buffer);
}

void RandomShuffleSpan()
{
var random = new Random();
Span<byte> span = new byte[10];
random.Shuffle(span);
}
#endif

void RandomShuffle()
{
var random = new Random();
var buffer = new byte[10];
random.Shuffle(buffer);
}

public void SortedList()
{
var list = new SortedList<int, char>();
Expand Down
63 changes: 63 additions & 0 deletions src/Polyfill/Polyfill_Random.cs
Original file line number Diff line number Diff line change
Expand Up @@ -24,4 +24,67 @@ public static void NextBytes(
array.CopyTo(buffer);
}
#endif

#if !NET8_0_OR_GREATER

/// <summary>
/// Performs an in-place shuffle of an array.
/// </summary>
/// <param name="index">The array to shuffle.</param>
/// <typeparam name="T">The type of array.</typeparam>
/// <remarks>
/// This method uses <see cref="Next(int, int)" /> to choose values for shuffling.
/// This method is an O(n) operation.
/// </remarks>
[Link("https://learn.microsoft.com/en-us/dotnet/api/system.random.nextbytes#system-random-nextbytes(system-span((system-byte)))")]
public static void Shuffle<T>(
this Random target,
T[] values)
{
int n = values.Length;

for (int i = 0; i < n - 1; i++)
{
int j = target.Next(i, n);

if (j != i)
{
T temp = values[i];
values[i] = values[j];
values[j] = temp;
}
}
}
#if FeatureMemory

/// <summary>
/// Performs an in-place shuffle of a span.
/// </summary>
/// <param name="index">The span to shuffle.</param>
/// <typeparam name="T">The type of span.</typeparam>
/// <remarks>
/// This method uses <see cref="Next(int, int)" /> to choose values for shuffling.
/// This method is an O(n) operation.
/// </remarks>
[Link("https://learn.microsoft.com/en-us/dotnet/api/system.random.nextbytes#system-random-nextbytes(system-span((system-byte)))")]
public static void Shuffle<T>(
this Random target,
Span<T> values)
{
int n = values.Length;

for (int i = 0; i < n - 1; i++)
{
int j = target.Next(i, n);

if (j != i)
{
T temp = values[i];
values[i] = values[j];
values[j] = temp;
}
}
}
#endif
#endif
}
24 changes: 18 additions & 6 deletions src/Tests/PolyfillTests_Random.cs
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,29 @@ partial class PolyfillTests
[Test]
public void RandomNextBytesSpan()
{
// Create a new instance of Random
var random = new Random();

// Create a span of bytes
Span<byte> buffer = new byte[10];

// Fill the span with random bytes
random.NextBytes(buffer);
Assert.IsTrue(buffer.ToArray().Any(b => b != 0));
}

// Assert that the span is filled with random bytes
[Test]
public void RandomShuffleSpan()
{
var random = new Random();
Span<byte> buffer = new byte[10];
random.NextBytes(buffer);
random.Shuffle(buffer);
Assert.IsTrue(buffer.ToArray().Any(b => b != 0));
}
#endif
[Test]
public void RandomShuffleArray()
{
var random = new Random();
var buffer = new byte[10];
random.NextBytes(buffer);
random.Shuffle(buffer);
Assert.IsTrue(buffer.ToArray().Any(b => b != 0));
}
}

0 comments on commit 6c1b1ff

Please sign in to comment.