diff --git a/Ramstack.Structures.Tests/Collections/ArrayViewExtensionsTests.cs b/Ramstack.Structures.Tests/Collections/ArrayViewExtensionsTests.cs new file mode 100644 index 0000000..9ee94c8 --- /dev/null +++ b/Ramstack.Structures.Tests/Collections/ArrayViewExtensionsTests.cs @@ -0,0 +1,29 @@ +namespace Ramstack.Collections; + +[TestFixture] +public class ArrayViewExtensionsTests +{ + #if NET9_0_OR_GREATER + + [Test] + public void List_AsView_Empty() + { + var list = new List(); + var view = list.AsView(); + + Assert.That(view.Length, Is.EqualTo(list.Count)); + Assert.That(view, Is.EquivalentTo(list)); + } + + [Test] + public void List_AsView() + { + var list = new List { "apple", "banana", "cherry", "kiwi", "elderberry" }; + var view = list.AsView(); + + Assert.That(view.Length, Is.EqualTo(list.Count)); + Assert.That(view, Is.EquivalentTo(list)); + } + + #endif +} diff --git a/Ramstack.Structures.Tests/Ramstack.Structures.Tests.csproj b/Ramstack.Structures.Tests/Ramstack.Structures.Tests.csproj index 0d59e66..36812f6 100644 --- a/Ramstack.Structures.Tests/Ramstack.Structures.Tests.csproj +++ b/Ramstack.Structures.Tests/Ramstack.Structures.Tests.csproj @@ -1,6 +1,6 @@ - net6.0;net7.0;net8.0 + net6.0;net7.0;net8.0;net9.0 enable enable preview diff --git a/Ramstack.Structures/Collections/ArrayViewExtensions.cs b/Ramstack.Structures/Collections/ArrayViewExtensions.cs index 2676e02..cfcc314 100644 --- a/Ramstack.Structures/Collections/ArrayViewExtensions.cs +++ b/Ramstack.Structures/Collections/ArrayViewExtensions.cs @@ -133,4 +133,52 @@ static int Impl(ReadOnlySpan span, T value, IEqualityComparer? comparer) return -1; } } + + #if NET9_0_OR_GREATER + + /// + /// Returns an over the specified list. + /// Items should not be added or removed from the + /// while the is in use. + /// + /// The type of the elements in the list. + /// The list to get the data view over. + /// + /// A instance over the specified list. + /// + public static ArrayView AsView(this List? list) + { + if (list is not null) + { + var count = list.Count; + var array = ListAccessor.GetBuffer(list); + + return new ArrayView(array, 0, Math.Min(count, array.Length)); + } + + return ArrayView.Empty; + } + + #region Inner type: ListAccessor + + /// + /// Provides low-level access to the internal array buffer of a . + /// + /// The type of the elements in the list. + private static class ListAccessor + { + /// + /// Retrieves a reference to the internal array buffer of the specified . + /// + /// The list whose internal buffer is to be accessed. + /// + /// A reference to the internal array used by the list. + /// + [UnsafeAccessor(UnsafeAccessorKind.Field, Name = "_items")] + public static extern ref T[] GetBuffer(List list); + } + + #endregion + + #endif } diff --git a/Ramstack.Structures/Ramstack.Structures.csproj b/Ramstack.Structures/Ramstack.Structures.csproj index 732bef6..ffa5aaf 100644 --- a/Ramstack.Structures/Ramstack.Structures.csproj +++ b/Ramstack.Structures/Ramstack.Structures.csproj @@ -1,6 +1,6 @@ - net6.0;net8.0 + net6.0;net8.0;net9.0 Provides various data structures and utilities. Includes three primary types: