|
using System.Collections; |
|
using System.Runtime.CompilerServices; |
|
// using DelegateTo; |
|
|
|
namespace ConsoleApp1; |
|
|
|
class Program |
|
{ |
|
[MethodImpl(MethodImplOptions.NoInlining | MethodImplOptions.AggressiveOptimization)] |
|
static void Main(string[] args) |
|
{ |
|
MyArrayWrap<int> arr = CreateArray(); |
|
|
|
// (new int[5]).AsSpan() |
|
var kek = arr.Where(new PredIntIsEven()); |
|
|
|
// var kek = arr.GetEnumerator().Where(new PredIntIsEven()); |
|
foreach (int item in kek) |
|
{ |
|
Console.WriteLine(item); |
|
} |
|
} |
|
|
|
|
|
[MethodImpl(MethodImplOptions.NoInlining)] |
|
private static MyArrayWrap<int> CreateArray() |
|
{ |
|
return new MyArrayWrap<int>{array = new []{1,1,1,1,2,2,3,4,5,6,7,8,9}}; |
|
} |
|
} |
|
|
|
public struct PredIntIsEven: IPredicate<int> |
|
{ |
|
// [MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
public bool Matches(in int item) |
|
{ |
|
return (item & 1) == 0; |
|
// return item > 5 ; |
|
} |
|
} |
|
|
|
|
|
public interface IPredicate<T>{ |
|
[MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
bool Matches(in T item); |
|
|
|
|
|
} |
|
|
|
// public static class MyArrayWrapExt { |
|
// |
|
// [MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
// public static WhereEnumerable<T, TInner, TInnerIter, TPredicate> Where<T, TInner, TInnerIter, TPredicate>(this TInner @this, TPredicate predicate) |
|
// where TInner : IIterable<T, TInnerIter> |
|
// where TInnerIter:IITerator<T> |
|
// where TPredicate : IPredicate<T> |
|
// { |
|
// return new WhereEnumerable<T, TInner, TInnerIter, TPredicate>(@this, predicate); |
|
// } |
|
// |
|
// } |
|
|
|
public struct WhereEnumerable<T, TInner, TInnerIter, TPredicate > : IIterable<T, WhereEnumerable<T, TInner, TInnerIter, TPredicate >, WhereEnumerator<T, TInnerIter, TPredicate>> |
|
where TInner : IIterable<T, TInner, TInnerIter> |
|
where TInnerIter:IITerator<T> |
|
where TPredicate:IPredicate<T> |
|
{ |
|
private TInner _inner; |
|
private TPredicate _predicate; |
|
|
|
public WhereEnumerable(TInner inner, TPredicate predicate) |
|
{ |
|
_inner = inner; |
|
_predicate = predicate; |
|
} |
|
|
|
public WhereEnumerator<T, TInnerIter, TPredicate> GetEnumerator() => new(_inner.GetEnumerator(), _predicate); |
|
} |
|
|
|
public struct WhereEnumerator<T, TInnerIter, TPredicate> : IITerator<T> where TInnerIter:IITerator<T> where TPredicate:IPredicate<T> |
|
{ |
|
private TInnerIter _inner; |
|
private TPredicate _predicate; |
|
|
|
[MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
public WhereEnumerator(TInnerIter inner, TPredicate predicate) |
|
{ |
|
_inner = inner; |
|
_predicate = predicate; |
|
} |
|
|
|
[MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
public bool MoveNext() |
|
{ |
|
do |
|
{ |
|
if (!_inner.MoveNext()) |
|
return false; |
|
|
|
} while (!_predicate.Matches(_inner.Current)); |
|
|
|
return true; |
|
} |
|
|
|
public ref T Current |
|
{ |
|
[MethodImpl(MethodImplOptions.AggressiveInlining)] get => ref this._inner.Current; |
|
} |
|
|
|
|
|
[MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
public void Dispose() |
|
{ |
|
|
|
} |
|
} |
|
|
|
public interface IITerator<T>:IDisposable |
|
{ |
|
bool MoveNext(); |
|
public ref T Current { get; } |
|
} |
|
|
|
public interface IIterable<T, Self, TIter> |
|
where TIter : IITerator<T> |
|
where Self : IIterable<T, Self, TIter> |
|
{ |
|
TIter GetEnumerator(); |
|
|
|
// [MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
// public WhereEnumerable<T, Self, TIter, TPredicate> Where<TPredicate>( TPredicate predicate) |
|
// where TPredicate : IPredicate<T> |
|
// { |
|
// return new WhereEnumerable<T, Self, TIter, TPredicate>((Self)this, predicate); |
|
// } |
|
} |
|
|
|
public struct MethodsImpl<T, Self, TIter> |
|
where TIter : IITerator<T> |
|
where Self : IIterable<T, Self, TIter> |
|
{ |
|
private Self self; |
|
|
|
public MethodsImpl(Self self) |
|
{ |
|
this.self = self; |
|
} |
|
|
|
[MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
public WhereEnumerable<T, Self, TIter, TPredicate> Where<TPredicate>( TPredicate predicate) |
|
where TPredicate : IPredicate<T> |
|
{ |
|
return new WhereEnumerable<T, Self, TIter, TPredicate>(self, predicate); |
|
} |
|
} |
|
|
|
|
|
|
|
|
|
|
|
public partial struct MyArrayWrap<T> : IIterable<T, MyArrayWrap<T>, MyArrayWrap<T>.Enumerator> |
|
{ |
|
public T[] array; |
|
|
|
|
|
public Enumerator GetEnumerator() => new Enumerator(this.array); |
|
|
|
|
|
|
|
// [GenerateDelegate(Inline = true)] |
|
// public MethodsImpl<T, MyArrayWrap<T>, Enumerator> Methods |
|
// { |
|
// [MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
// get |
|
// { |
|
// return new MethodsImpl<T, MyArrayWrap<T>, Enumerator>( this); |
|
// } |
|
// } |
|
|
|
[MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
public WhereEnumerable<T, MyArrayWrap<T>, Enumerator, TPredicate> Where<TPredicate>( TPredicate predicate) |
|
where TPredicate : IPredicate<T> |
|
{ |
|
return new WhereEnumerable<T, MyArrayWrap<T>, Enumerator, TPredicate>(this, predicate); |
|
} |
|
|
|
public struct Enumerator : IITerator<T> |
|
{ |
|
private T[] _array; |
|
private int _index; |
|
|
|
[MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
public Enumerator(T[] array) |
|
{ |
|
_array = array; |
|
_index = -1; |
|
} |
|
|
|
[MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
public bool MoveNext() |
|
{ |
|
int num = this._index + 1; |
|
if (num >= this._array.Length) |
|
return false; |
|
this._index = num; |
|
return true; |
|
} |
|
|
|
[MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
public void Reset() |
|
{ |
|
_index = -1; |
|
} |
|
|
|
public ref T Current |
|
{ |
|
[MethodImpl(MethodImplOptions.AggressiveInlining)] get => ref this._array[this._index]; |
|
} |
|
|
|
|
|
[MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
public void Dispose() |
|
{ |
|
|
|
} |
|
} |
|
|
|
} |