Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix Support for Collection Expressions #1323

Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
20 changes: 20 additions & 0 deletions LanguageExt.Core/CollectionBuilderAttribute.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
namespace System.Runtime.CompilerServices
{
[AttributeUsage(
AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Interface,
Inherited = false,
AllowMultiple = false)]
public sealed class CollectionBuilderAttribute : Attribute
{
public CollectionBuilderAttribute(
Type builderType,
string methodName)
{
BuilderType = builderType;
MethodName = methodName;
}

public Type BuilderType { get; }
public string MethodName { get; }
}
}
11 changes: 11 additions & 0 deletions LanguageExt.Core/Immutable Collections/Arr/Arr.Module.cs
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,17 @@ public static partial class Arr
[Pure]
public static Arr<T> create<T>(params T[] items) =>
new Arr<T>(items);

/// <summary>
/// Create an array from a initial set of items
/// </summary>
/// <param name="items">Items</param>
/// <returns>Lst T</returns>
[Pure]
public static Arr<T> create<T>(
ReadOnlySpan<T> items) =>
create(
items.ToArray());

/// <summary>
/// Create an array from an initial set of items
Expand Down
5 changes: 4 additions & 1 deletion LanguageExt.Core/Immutable Collections/Arr/Arr.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
using System.Linq;
using System.Collections;
using System.Collections.Generic;
using System.ComponentModel;
using System.Diagnostics.Contracts;
using static LanguageExt.Prelude;
using LanguageExt.TypeClasses;
Expand All @@ -17,6 +18,9 @@ namespace LanguageExt
/// for large arrays.
/// </summary>
/// <typeparam name="A">Value type</typeparam>
[CollectionBuilderAttribute(
typeof(Arr),
nameof(Arr.create))]
[Serializable]
public struct Arr<A> :
IEnumerable<A>,
Expand Down Expand Up @@ -721,6 +725,5 @@ public Arr<B> Bind<B>(Func<A, Arr<B>> f)
[MethodImpl(MethodImplOptions.AggressiveInlining)]
public static implicit operator Arr<A>(SeqEmpty _) =>
Empty;

}
}
11 changes: 11 additions & 0 deletions LanguageExt.Core/Immutable Collections/List/Lst.Module.cs
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,17 @@ public static partial class List
public static Lst<T> create<T>(params T[] items) =>
new Lst<T>(items);

/// <summary>
/// Create an array from a initial set of items
/// </summary>
/// <param name="items">Items</param>
/// <returns>Lst T</returns>
[Pure]
public static Lst<T> create<T>(
ReadOnlySpan<T> items) =>
create(
items.ToArray());

/// <summary>
/// Create a list from an initial set of items
/// </summary>
Expand Down
3 changes: 3 additions & 0 deletions LanguageExt.Core/Immutable Collections/List/Lst.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@ namespace LanguageExt
/// Immutable list
/// </summary>
/// <typeparam name="A">Value type</typeparam>
[CollectionBuilder(
typeof(List),
nameof(List.create))]
[Serializable]
public readonly struct Lst<A> :
IComparable<Lst<A>>,
Expand Down
11 changes: 11 additions & 0 deletions LanguageExt.Core/Immutable Collections/Seq/Seq.Module.cs
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,17 @@ public static Seq<A> create<A>(params A[] items)
System.Array.Copy(items, nitems, items.Length);
return FromArray(items);
}

/// <summary>
/// Create an array from a initial set of items
/// </summary>
/// <param name="items">Items</param>
/// <returns>Lst T</returns>
[Pure]
public static Seq<T> create<T>(
ReadOnlySpan<T> items) =>
create(
items.ToArray());

/// <summary>
/// Create a sequence from an initial set of items
Expand Down
3 changes: 3 additions & 0 deletions LanguageExt.Core/Immutable Collections/Seq/Seq.cs
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,9 @@ namespace LanguageExt
/// </summary>
/// <typeparam name="A">Type of the values in the sequence</typeparam>

[CollectionBuilder(
typeof(Seq),
nameof(Seq.create))]
public readonly struct Seq<A> :
#pragma warning disable CS0618 // Remove ISeq complaint
ISeq<A>,
Expand Down
10 changes: 10 additions & 0 deletions LanguageExt.Core/Immutable Collections/Set/Set.Module.cs
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,16 @@ public static partial class Set
public static Set<T> create<T>() =>
Set<T>.Empty;

/// <summary>
/// Create an array from a initial set of items
/// </summary>
/// <param name="items">Items</param>
/// <returns>Lst T</returns>
[Pure]
public static Set<T> create<T>(
ReadOnlySpan<T> items) =>
new Set<T>(items.ToArray());

/// <summary>
/// Create a new set pre-populated with the items in range
/// </summary>
Expand Down
3 changes: 3 additions & 0 deletions LanguageExt.Core/Immutable Collections/Set/Set.cs
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,9 @@ namespace LanguageExt
/// [wikipedia.org/wiki/AVL_tree](http://en.wikipedia.org/wiki/AVL_tree)
/// </summary>
/// <typeparam name="A">Set item type</typeparam>
[CollectionBuilder(
typeof(Set),
nameof(Set.create))]
[Serializable]
public readonly struct Set<A> :
IEnumerable<A>,
Expand Down
13 changes: 13 additions & 0 deletions LanguageExt.Tests/ArrayTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -174,5 +174,18 @@ public void itemOrNoneLensGetShouldReturnNoneForNonExistingValue()

Assert.Equal(expected, actual);
}

/// See https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/proposals/csharp-12.0/collection-expressions#create-methods
[Fact]
public void CollectionExpressions()
{
Arr<int> array = [1, 2, 3, 4, 5];

Assert.Equal(5, array.Length);

Arr<int> array2 = [99, ..array];

Assert.Equal(6, array2.Length);
}
}
}
13 changes: 13 additions & 0 deletions LanguageExt.Tests/ListTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -618,5 +618,18 @@ public void itemOrNoneLensGetShouldReturnNoneForNonExistingValue()

Assert.Equal(expected, actual);
}

/// See https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/proposals/csharp-12.0/collection-expressions#create-methods
[Fact]
public void CollectionExpressions()
{
Lst<int> lst = [1, 2, 3, 4, 5];

Assert.Equal(5, lst.Count);

Lst<int> seq2 = [99, ..lst];

Assert.Equal(6, seq2.Count);
}
}
}
13 changes: 13 additions & 0 deletions LanguageExt.Tests/SeqTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -665,5 +665,18 @@ public async Task SequenceParallelRandomDelayTest()
return seconds;
}
}

/// See https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/proposals/csharp-12.0/collection-expressions#create-methods
[Fact]
public void CollectionExpressions()
{
Seq<int> seq = [1, 2, 3, 4, 5];

Assert.Equal(5, seq.Length);

Seq<int> seq2 = [99, ..seq];

Assert.Equal(6, seq2.Length);
}
}
}
13 changes: 13 additions & 0 deletions LanguageExt.Tests/SetTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -485,5 +485,18 @@ public void CaseTest()
{ Assert.True(Set<OrdInt, int>(1).Case is not var (_, _) and 1); }
{ Assert.True(Set<OrdInt, int>(1, 2).Case is (1, Seq<int> xs) && xs == Seq1(2)); }
}

/// See https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/proposals/csharp-12.0/collection-expressions#create-methods
[Fact]
public void CollectionExpressions()
{
Set<int> set = [1, 2, 3, 3, 4, 5];

Assert.Equal(5, set.Count);

Set<int> set2 = [3, ..set, 99];

Assert.Equal(6, set2.Count);
}
}
}