Skip to content
This repository was archived by the owner on Jan 23, 2023. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
20 commits
Select commit Hold shift + click to select a range
53c16cf
Add ROSpan StartsWith and EndsWith string-like APIs with StringCompar…
ahsonkhan Feb 6, 2018
18e7f69
We have separate implementations of slow and fast span.
ahsonkhan Feb 6, 2018
a257e3b
Remove unused using directive.
ahsonkhan Feb 6, 2018
ddfb49d
Address PR feedback and add tests.
ahsonkhan Feb 6, 2018
8df2742
Add test files
ahsonkhan Feb 6, 2018
5c8114d
Get the string from the underlying span to avoid allocation when poss…
ahsonkhan Feb 7, 2018
273bc7e
Update ToString and add tests
ahsonkhan Feb 7, 2018
2d5444b
Update Span ToString and add tests
ahsonkhan Feb 7, 2018
041692a
Merge branch 'master' of https://github.com/dotnet/corefx into AddSta…
ahsonkhan Feb 8, 2018
162a710
Address PR feedback and disable ToString test for fast span
ahsonkhan Feb 9, 2018
a090776
Borrow additional tests from the existing StringTests test bed.
ahsonkhan Feb 9, 2018
839bf29
Fix comment grammar
ahsonkhan Feb 9, 2018
8aaf7c2
No StringComparison results in generic StartsWith being called which …
ahsonkhan Feb 9, 2018
410240f
Merge branch 'master' of https://github.com/dotnet/corefx into AddSta…
ahsonkhan Feb 10, 2018
7d0fa71
Address feedback related to ToString and tests
ahsonkhan Feb 16, 2018
4bac971
Fix tests for culture specific cases, for Unix.
ahsonkhan Feb 16, 2018
a2ada65
Fix typo in variable names
ahsonkhan Feb 16, 2018
8f9ca8c
Merge branch 'master' of https://github.com/dotnet/corefx into AddSta…
ahsonkhan Feb 21, 2018
b9167c2
Respond to recent change AsReadOnlySpan -> AsSpan
ahsonkhan Feb 21, 2018
4b9d13e
Fix typo in test.
ahsonkhan Feb 21, 2018
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 13 additions & 13 deletions src/System.Memory/ref/System.Memory.cs
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ public static partial class MemoryExtensions
public static int BinarySearch<T, TComparable>(this System.Span<T> span, TComparable comparable) where TComparable : System.IComparable<T> { throw null; }
public static void CopyTo<T>(this T[] array, System.Memory<T> destination) { }
public static void CopyTo<T>(this T[] array, System.Span<T> destination) { }
public static bool EndsWith(this System.ReadOnlySpan<char> span, System.ReadOnlySpan<char> value, System.StringComparison comparisonType) { throw null; }
public static bool EndsWith<T>(this System.ReadOnlySpan<T> span, System.ReadOnlySpan<T> value) where T : System.IEquatable<T> { throw null; }
public static bool EndsWith<T>(this System.Span<T> span, System.ReadOnlySpan<T> value) where T : System.IEquatable<T> { throw null; }
public static int IndexOfAny<T>(this System.ReadOnlySpan<T> span, System.ReadOnlySpan<T> values) where T : System.IEquatable<T> { throw null; }
Expand Down Expand Up @@ -63,6 +64,7 @@ public static void Reverse<T>(this System.Span<T> span) { }
public static int SequenceCompareTo<T>(this System.Span<T> first, System.ReadOnlySpan<T> second) where T : System.IComparable<T> { throw null; }
public static bool SequenceEqual<T>(this System.ReadOnlySpan<T> first, System.ReadOnlySpan<T> second) where T : System.IEquatable<T> { throw null; }
public static bool SequenceEqual<T>(this System.Span<T> first, System.ReadOnlySpan<T> second) where T : System.IEquatable<T> { throw null; }
public static bool StartsWith(this System.ReadOnlySpan<char> span, System.ReadOnlySpan<char> value, System.StringComparison comparisonType) { throw null; }
public static bool StartsWith<T>(this System.ReadOnlySpan<T> span, System.ReadOnlySpan<T> value) where T : System.IEquatable<T> { throw null; }
public static bool StartsWith<T>(this System.Span<T> span, System.ReadOnlySpan<T> value) where T : System.IEquatable<T> { throw null; }
public static System.ReadOnlySpan<char> Trim(this System.ReadOnlySpan<char> span) { throw null; }
Expand Down Expand Up @@ -91,7 +93,6 @@ public void CopyTo(System.Memory<T> destination) { }
public override bool Equals(object obj) { throw null; }
[System.ComponentModel.EditorBrowsableAttribute((System.ComponentModel.EditorBrowsableState)(1))]
public override int GetHashCode() { throw null; }
public override string ToString() { throw null; }
public static implicit operator System.Memory<T> (System.ArraySegment<T> arraySegment) { throw null; }
public static implicit operator System.ReadOnlyMemory<T> (System.Memory<T> memory) { throw null; }
public static implicit operator System.Memory<T> (T[] array) { throw null; }
Expand All @@ -117,7 +118,6 @@ public void CopyTo(System.Memory<T> destination) { }
public bool Equals(System.ReadOnlyMemory<T> other) { throw null; }
[System.ComponentModel.EditorBrowsableAttribute((System.ComponentModel.EditorBrowsableState)(1))]
public override int GetHashCode() { throw null; }
public override string ToString() { throw null; }
public static implicit operator System.ReadOnlyMemory<T> (System.ArraySegment<T> arraySegment) { throw null; }
public static implicit operator System.ReadOnlyMemory<T> (T[] array) { throw null; }
public System.Buffers.MemoryHandle Retain(bool pin = false) { throw null; }
Expand Down Expand Up @@ -145,14 +145,14 @@ public void CopyTo(System.Span<T> destination) { }
[System.ComponentModel.EditorBrowsableAttribute((System.ComponentModel.EditorBrowsableState)(1))]
[System.ObsoleteAttribute("GetHashCode() on ReadOnlySpan will always throw an exception.")]
public override int GetHashCode() { throw null; }
public override string ToString() { throw null; }
public static bool operator ==(System.ReadOnlySpan<T> left, System.ReadOnlySpan<T> right) { throw null; }
public static implicit operator System.ReadOnlySpan<T> (System.ArraySegment<T> arraySegment) { throw null; }
public static implicit operator System.ReadOnlySpan<T> (T[] array) { throw null; }
public static bool operator !=(System.ReadOnlySpan<T> left, System.ReadOnlySpan<T> right) { throw null; }
public System.ReadOnlySpan<T> Slice(int start) { throw null; }
public System.ReadOnlySpan<T> Slice(int start, int length) { throw null; }
public T[] ToArray() { throw null; }
public override string ToString() { throw null; }
public bool TryCopyTo(System.Span<T> destination) { throw null; }
public ref partial struct Enumerator
{
Expand Down Expand Up @@ -196,7 +196,6 @@ public void Fill(T value) { }
[System.ComponentModel.EditorBrowsableAttribute((System.ComponentModel.EditorBrowsableState)(1))]
[System.ObsoleteAttribute("GetHashCode() on Span will always throw an exception.")]
public override int GetHashCode() { throw null; }
public override string ToString() { throw null; }
public static bool operator ==(System.Span<T> left, System.Span<T> right) { throw null; }
public static implicit operator System.Span<T> (System.ArraySegment<T> arraySegment) { throw null; }
public static implicit operator System.ReadOnlySpan<T> (System.Span<T> span) { throw null; }
Expand All @@ -205,6 +204,7 @@ public void Fill(T value) { }
public System.Span<T> Slice(int start) { throw null; }
public System.Span<T> Slice(int start, int length) { throw null; }
public T[] ToArray() { throw null; }
public override string ToString() { throw null; }
public bool TryCopyTo(System.Span<T> destination) { throw null; }
public ref partial struct Enumerator
{
Expand Down Expand Up @@ -244,14 +244,14 @@ public partial struct MemoryHandle : System.IDisposable
public unsafe void* Pointer { get { throw null; } }
public void Dispose() { }
}
public abstract class MemoryPool<T> : IDisposable
public abstract partial class MemoryPool<T> : System.IDisposable
{
public static System.Buffers.MemoryPool<T> Shared { get; }
public abstract System.Buffers.OwnedMemory<T> Rent(int minBufferSize=-1);
protected MemoryPool() { }
public abstract int MaxBufferSize { get; }
protected MemoryPool() { throw null; }
public void Dispose() { throw null; }
public static System.Buffers.MemoryPool<T> Shared { get { throw null; } }
public void Dispose() { }
protected abstract void Dispose(bool disposing);
public abstract System.Buffers.OwnedMemory<T> Rent(int minBufferSize = -1);
}
public enum OperationStatus
{
Expand Down Expand Up @@ -497,15 +497,15 @@ namespace System.Runtime.InteropServices
public static partial class MemoryMarshal
{
public static System.Memory<T> AsMemory<T>(System.ReadOnlyMemory<T> readOnlyMemory) { throw null; }
public static ref T GetReference<T>(System.ReadOnlySpan<T> span) { throw null; }
public static ref T GetReference<T>(System.Span<T> span) { throw null; }
public static bool TryGetArray<T>(System.ReadOnlyMemory<T> readOnlyMemory, out System.ArraySegment<T> arraySegment) { throw null; }
public static System.Collections.Generic.IEnumerable<T> ToEnumerable<T>(ReadOnlyMemory<T> memory) { throw null; }
public static System.ReadOnlySpan<TTo> Cast<TFrom, TTo>(System.ReadOnlySpan<TFrom> source) where TFrom : struct where TTo : struct { throw null; }
public static System.Span<TTo> Cast<TFrom, TTo>(System.Span<TFrom> source) where TFrom : struct where TTo : struct { throw null; }
#if !FEATURE_PORTABLE_SPAN
public static System.ReadOnlySpan<T> CreateReadOnlySpan<T>(ref T reference, int length) { throw null; }
public static System.Span<T> CreateSpan<T>(ref T reference, int length) { throw null; }
#endif
public static ref T GetReference<T>(System.ReadOnlySpan<T> span) { throw null; }
public static ref T GetReference<T>(System.Span<T> span) { throw null; }
public static System.Collections.Generic.IEnumerable<T> ToEnumerable<T>(System.ReadOnlyMemory<T> memory) { throw null; }
public static bool TryGetArray<T>(System.ReadOnlyMemory<T> readOnlyMemory, out System.ArraySegment<T> arraySegment) { throw null; }
}
}
18 changes: 18 additions & 0 deletions src/System.Memory/src/System/MemoryExtensions.Fast.cs
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,24 @@ namespace System
/// </summary>
public static partial class MemoryExtensions
{
/// <summary>
/// Determines whether the end of the <paramref name="span"/> matches the specified <paramref name="value"/> when compared using the specified <paramref name="comparisonType"/> option.
/// </summary>
/// <param name="span">The source span.</param>
/// <param name="value">The sequence to compare to the end of the source span.</param>
/// <param name="comparisonType">One of the enumeration values that determines how the <paramref name="span"/> and <paramref name="value"/> are compared.</param>
public static bool EndsWith(this ReadOnlySpan<char> span, ReadOnlySpan<char> value, StringComparison comparisonType)
=> Span.EndsWith(span, value, comparisonType);

/// <summary>
/// Determines whether the beginning of the <paramref name="span"/> matches the specified <paramref name="value"/> when compared using the specified <paramref name="comparisonType"/> option.
/// </summary>
/// <param name="span">The source span.</param>
/// <param name="value">The sequence to compare to the beginning of the source span.</param>
/// <param name="comparisonType">One of the enumeration values that determines how the <paramref name="span"/> and <paramref name="value"/> are compared.</param>
public static bool StartsWith(this ReadOnlySpan<char> span, ReadOnlySpan<char> value, StringComparison comparisonType)
=> Span.StartsWith(span, value, comparisonType);

/// <summary>
/// Casts a Span of one primitive type <typeparamref name="T"/> to Span of bytes.
/// That type may not contain pointers or references. This is checked at runtime in order to preserve type safety.
Expand Down
36 changes: 36 additions & 0 deletions src/System.Memory/src/System/MemoryExtensions.Portable.cs
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,42 @@ namespace System
/// </summary>
public static partial class MemoryExtensions
{
/// <summary>
/// Determines whether the end of the <paramref name="span"/> matches the specified <paramref name="value"/> when compared using the specified <paramref name="comparisonType"/> option.
/// </summary>
/// <param name="span">The source span.</param>
/// <param name="value">The sequence to compare to the end of the source span.</param>
/// <param name="comparisonType">One of the enumeration values that determines how the <paramref name="span"/> and <paramref name="value"/> are compared.</param>
public static bool EndsWith(this ReadOnlySpan<char> span, ReadOnlySpan<char> value, StringComparison comparisonType)
{
if (comparisonType == StringComparison.Ordinal)
{
return span.EndsWith<char>(value);
}

string sourceString = span.ToString();
string valueString = value.ToString();
return sourceString.EndsWith(valueString, comparisonType);
}

/// <summary>
/// Determines whether the beginning of the <paramref name="span"/> matches the specified <paramref name="value"/> when compared using the specified <paramref name="comparisonType"/> option.
/// </summary>
/// <param name="span">The source span.</param>
/// <param name="value">The sequence to compare to the beginning of the source span.</param>
/// <param name="comparisonType">One of the enumeration values that determines how the <paramref name="span"/> and <paramref name="value"/> are compared.</param>
public static bool StartsWith(this ReadOnlySpan<char> span, ReadOnlySpan<char> value, StringComparison comparisonType)
{
if (comparisonType == StringComparison.Ordinal)
{
return span.StartsWith<char>(value);
}

string sourceString = span.ToString();
string valueString = value.ToString();
return sourceString.StartsWith(valueString, comparisonType);
}

/// <summary>
/// Casts a Span of one primitive type <typeparamref name="T"/> to Span of bytes.
/// That type may not contain pointers or references. This is checked at runtime in order to preserve type safety.
Expand Down
11 changes: 11 additions & 0 deletions src/System.Memory/src/System/ReadOnlySpan.Portable.cs
Original file line number Diff line number Diff line change
Expand Up @@ -193,6 +193,17 @@ public override string ToString()
{
if (typeof(T) == typeof(char))
{
// If this wraps a string and represents the full length of the string, just return the wrapped string.
if (_byteOffset == MemoryExtensions.StringAdjustment)
{
object obj = Unsafe.As<object>(_pinnable); // minimize chances the compilers will optimize away the 'is' check
if (obj is string str && _length == str.Length)
{
return str;
}
}

// Otherwise, copy the data to a new string.
unsafe
{
fixed (char* src = &Unsafe.As<T, char>(ref DangerousGetPinnableReference()))
Expand Down
Loading