Average, MinMax, and others

This commit is contained in:
neuecc
2020-05-09 15:33:46 +09:00
parent c16433e0fe
commit d4511c0f67
20 changed files with 8208 additions and 1459 deletions

View File

@@ -0,0 +1,122 @@
using System;
using System.Runtime.CompilerServices;
using System.Threading.Tasks;
using System.Threading.Tasks.Sources;
namespace Cysharp.Threading.Tasks
{
public static class UniTaskValueTaskExtensions
{
public static ValueTask AsValueTask(this UniTask task)
{
ref var core = ref Unsafe.As<UniTask, UniTaskToValueTask>(ref task);
if (core.source == null)
{
return default;
}
return new ValueTask(new UniTaskValueTaskSource(core.source), core.token);
}
public static ValueTask<T> AsValueTask<T>(this UniTask<T> task)
{
ref var core = ref Unsafe.As<UniTask<T>, UniTaskToValueTask<T>>(ref task);
if (core.source == null)
{
return new ValueTask<T>(core.result);
}
return new ValueTask<T>(new UniTaskValueTaskSource<T>(core.source), core.token);
}
struct UniTaskToValueTask
{
public IUniTaskSource source;
public short token;
}
class UniTaskValueTaskSource : IValueTaskSource
{
readonly IUniTaskSource source;
public UniTaskValueTaskSource(IUniTaskSource source)
{
this.source = source;
}
public void GetResult(short token)
{
source.GetResult(token);
}
public ValueTaskSourceStatus GetStatus(short token)
{
var status = source.GetStatus(token);
switch (status)
{
case UniTaskStatus.Pending:
return ValueTaskSourceStatus.Pending;
case UniTaskStatus.Succeeded:
return ValueTaskSourceStatus.Succeeded;
case UniTaskStatus.Faulted:
return ValueTaskSourceStatus.Faulted;
case UniTaskStatus.Canceled:
return ValueTaskSourceStatus.Canceled;
default:
return (ValueTaskSourceStatus)status;
}
}
public void OnCompleted(Action<object> continuation, object state, short token, ValueTaskSourceOnCompletedFlags flags)
{
source.OnCompleted(continuation, state, token);
}
}
struct UniTaskToValueTask<T>
{
public IUniTaskSource<T> source;
public T result;
public short token;
}
class UniTaskValueTaskSource<T> : IValueTaskSource<T>
{
readonly IUniTaskSource<T> source;
public UniTaskValueTaskSource(IUniTaskSource<T> source)
{
this.source = source;
}
public T GetResult(short token)
{
return source.GetResult(token);
}
public ValueTaskSourceStatus GetStatus(short token)
{
var status = source.GetStatus(token);
switch (status)
{
case UniTaskStatus.Pending:
return ValueTaskSourceStatus.Pending;
case UniTaskStatus.Succeeded:
return ValueTaskSourceStatus.Succeeded;
case UniTaskStatus.Faulted:
return ValueTaskSourceStatus.Faulted;
case UniTaskStatus.Canceled:
return ValueTaskSourceStatus.Canceled;
default:
return (ValueTaskSourceStatus)status;
}
}
public void OnCompleted(Action<object> continuation, object state, short token, ValueTaskSourceOnCompletedFlags flags)
{
source.OnCompleted(continuation, state, token);
}
}
}
}

View File

@@ -0,0 +1,112 @@
using System;
using System.Threading;
namespace Cysharp.Threading.Tasks
{
public partial struct UniTask
{
/// <summary>Run action on the threadPool and return to current SynchronizationContext if configureAwait = true.</summary>
public static async UniTask Run(Action action, bool configureAwait = true)
{
if (configureAwait)
{
var current = SynchronizationContext.Current;
await UniTask.SwitchToThreadPool();
try
{
action();
}
finally
{
if (current != null)
{
await UniTask.SwitchToSynchronizationContext(current);
}
}
}
else
{
await UniTask.SwitchToThreadPool();
action();
}
}
/// <summary>Run action on the threadPool and return to current SynchronizationContext if configureAwait = true.</summary>
public static async UniTask Run(Action<object> action, object state, bool configureAwait = true)
{
if (configureAwait)
{
var current = SynchronizationContext.Current;
await UniTask.SwitchToThreadPool();
try
{
action(state);
}
finally
{
if (current != null)
{
await UniTask.SwitchToSynchronizationContext(current);
}
}
}
else
{
await UniTask.SwitchToThreadPool();
action(state);
}
}
/// <summary>Run action on the threadPool and return to current SynchronizationContext if configureAwait = true.</summary>
public static async UniTask<T> Run<T>(Func<T> func, bool configureAwait = true)
{
if (configureAwait)
{
var current = SynchronizationContext.Current;
await UniTask.SwitchToThreadPool();
try
{
return func();
}
finally
{
if (current != null)
{
await UniTask.SwitchToSynchronizationContext(current);
}
}
}
else
{
await UniTask.SwitchToThreadPool();
return func();
}
}
/// <summary>Run action on the threadPool and return to current SynchronizationContext if configureAwait = true.</summary>
public static async UniTask<T> Run<T>(Func<object, T> func, object state, bool configureAwait = true)
{
if (configureAwait)
{
var current = SynchronizationContext.Current;
await UniTask.SwitchToThreadPool();
try
{
return func(state);
}
finally
{
if (current != null)
{
await UniTask.SwitchToSynchronizationContext(current);
}
}
}
else
{
await UniTask.SwitchToThreadPool();
return func(state);
}
}
}
}

View File

@@ -0,0 +1,55 @@
using System;
using System.Runtime.CompilerServices;
using System.Threading;
namespace Cysharp.Threading.Tasks
{
public partial struct UniTask
{
public static UniTask.YieldAwaitable Yield()
{
return default;
}
public readonly struct YieldAwaitable
{
public Awaiter GetAwaiter()
{
return default;
}
public readonly struct Awaiter : ICriticalNotifyCompletion
{
static readonly SendOrPostCallback SendOrPostCallbackDelegate = Continuation;
static readonly WaitCallback WaitCallbackDelegate = Continuation;
public bool IsCompleted => false;
public void GetResult() { }
public void OnCompleted(Action continuation)
{
UnsafeOnCompleted(continuation);
}
public void UnsafeOnCompleted(Action continuation)
{
var syncContext = SynchronizationContext.Current;
if (syncContext != null)
{
syncContext.Post(SendOrPostCallbackDelegate, continuation);
}
else
{
ThreadPool.UnsafeQueueUserWorkItem(WaitCallbackDelegate, continuation);
}
}
static void Continuation(object state)
{
((Action)state).Invoke();
}
}
}
}
}