From 140ee527530160c80e15ce4d103e89c5296ae560 Mon Sep 17 00:00:00 2001 From: sakno Date: Sat, 17 Aug 2024 22:03:59 +0300 Subject: [PATCH] Added span interop --- .../Runtime/ValueReferenceTests.cs | 28 ++++++++++++++++++- src/DotNext/Runtime/ValueReference.cs | 16 +++++++++++ 2 files changed, 43 insertions(+), 1 deletion(-) diff --git a/src/DotNext.Tests/Runtime/ValueReferenceTests.cs b/src/DotNext.Tests/Runtime/ValueReferenceTests.cs index b2ef52dda..3a1732c9a 100644 --- a/src/DotNext.Tests/Runtime/ValueReferenceTests.cs +++ b/src/DotNext.Tests/Runtime/ValueReferenceTests.cs @@ -85,14 +85,20 @@ public static void MutableEmptyRef() var reference = default(ValueReference); True(reference.IsEmpty); Null(reference.ToString()); + + Span span = reference; + True(span.IsEmpty); } - + [Fact] public static void ImmutableEmptyRef() { var reference = default(ReadOnlyValueReference); True(reference.IsEmpty); Null(reference.ToString()); + + ReadOnlySpan span = reference; + True(span.IsEmpty); } [Fact] @@ -167,6 +173,26 @@ public static void ArrayCovariance() Equal("b", roRef.Value); } + [Fact] + public static void SpanInterop() + { + var reference = new ValueReference(42); + Span span = reference; + Equal(1, span.Length); + + True(Unsafe.AreSame(in reference.Value, in span[0])); + } + + [Fact] + public static void ReadOnlySpanInterop() + { + ReadOnlyValueReference reference = new ValueReference(42); + ReadOnlySpan span = reference; + Equal(1, span.Length); + + True(Unsafe.AreSame(in reference.Value, in span[0])); + } + private record class MyClass : IResettable { internal static string StaticObject; diff --git a/src/DotNext/Runtime/ValueReference.cs b/src/DotNext/Runtime/ValueReference.cs index 1f10e6cbe..a7f7c6721 100644 --- a/src/DotNext/Runtime/ValueReference.cs +++ b/src/DotNext/Runtime/ValueReference.cs @@ -118,6 +118,14 @@ public bool Equals(ValueReference reference) /// The immutable field reference. public static implicit operator ReadOnlyValueReference(ValueReference reference) => Unsafe.BitCast, ReadOnlyValueReference>(reference); + + /// + /// Gets a span over the referenced value. + /// + /// The value reference. + /// The span that contains ; or empty span if is empty. + public static implicit operator Span(ValueReference reference) + => reference.IsEmpty ? new() : new(ref reference.Value); } /// @@ -205,6 +213,14 @@ public bool Equals(ReadOnlyValueReference reference) /// if both references are not equal; otherwise, . public static bool operator !=(ReadOnlyValueReference x, ReadOnlyValueReference y) => x.Equals(y) is false; + + /// + /// Gets a span over the referenced value. + /// + /// The value reference. + /// The span that contains ; or empty span if is empty. + public static implicit operator ReadOnlySpan(ReadOnlyValueReference reference) + => reference.IsEmpty ? new() : new(in reference.Value); } [SuppressMessage("Performance", "CA1812", Justification = "Used for reinterpret cast")]