Skip to content

Instantly share code, notes, and snippets.

@lnicola
Created June 26, 2014 12:19
Show Gist options
  • Save lnicola/42837ca4593bda6b3cde to your computer and use it in GitHub Desktop.
Save lnicola/42837ca4593bda6b3cde to your computer and use it in GitHub Desktop.
using System;
using System.Diagnostics;
using System.Threading.Tasks;
namespace ThreadRingTask
{
class Agent
{
public Agent Next;
private int id;
private TaskCompletionSource<int> taskCompletionSource;
private TaskCompletionSource<int> done;
public Agent(int id, TaskCompletionSource<int> done)
{
this.id = id;
this.done = done;
}
[System.Runtime.CompilerServices.MethodImpl(System.Runtime.CompilerServices.MethodImplOptions.NoInlining)]
public Task<int> Receive()
{
taskCompletionSource = new TaskCompletionSource<int>();
return taskCompletionSource.Task;
}
[System.Runtime.CompilerServices.MethodImpl(System.Runtime.CompilerServices.MethodImplOptions.NoInlining)]
public void Post(int value)
{
taskCompletionSource.SetResult(value);
}
public void Start()
{
Action<Task<int>> handler = null;
handler = t =>
{
var r = t.Result;
if (r == 0)
done.SetResult(id);
else
{
Receive().ContinueWith(handler, TaskContinuationOptions.ExecuteSynchronously);
Next.Post(t.Result - 1);
}
};
Receive().ContinueWith(handler, TaskContinuationOptions.ExecuteSynchronously);
}
}
class Program
{
static void Main()
{
var tcs = new TaskCompletionSource<int>();
var agents = new Agent[503];
for (var i = 0; i < agents.Length; i++)
agents[i] = new Agent(i, tcs);
for (var i = 0; i < agents.Length - 1; i++)
agents[i].Next = agents[i + 1];
agents[agents.Length - 1].Next = agents[0];
foreach (var agent in agents)
agent.Start();
var sw = Stopwatch.StartNew();
agents[0].Post(5000000);
var r = tcs.Task.Result;
sw.Stop();
Console.WriteLine(r);
Console.WriteLine(sw.ElapsedMilliseconds);
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment