Last active
March 26, 2019 19:03
-
-
Save stdray/d7a60ddeb1b5326347eab578924ff5ec to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
26.03.2019 21:43:33 | Begin thread 13 | |
26.03.2019 21:43:33 | Begin thread 15 | |
26.03.2019 21:43:33 | Begin thread 14 | |
26.03.2019 21:43:33 | Begin thread 16 | |
26.03.2019 21:43:33 | Process account account_6 in thread 16 | |
26.03.2019 21:43:33 | Process account account_7 in thread 14 | |
26.03.2019 21:43:33 | Process account account_4 in thread 15 | |
26.03.2019 21:43:33 | Process account account_5 in thread 13 | |
26.03.2019 21:43:33 | Process account account_3 in thread 16 | |
26.03.2019 21:43:33 | Process account account_2 in thread 14 | |
26.03.2019 21:43:35 | Process account account_1 in thread 16 | |
26.03.2019 21:43:36 | Process account account_1 locked for time: 26.03.2019 21:45:20 | |
26.03.2019 21:43:36 | Process account account_8 in thread 16 | |
26.03.2019 21:43:37 | Process account account_6 in thread 15 | |
26.03.2019 21:43:37 | Process account account_7 in thread 13 | |
26.03.2019 21:43:37 | Process account account_3 in thread 14 | |
26.03.2019 21:43:38 | Process account account_5 in thread 15 | |
26.03.2019 21:43:39 | Process account account_4 in thread 15 | |
26.03.2019 21:43:40 | Process account account_2 in thread 15 | |
26.03.2019 21:43:40 | Process account account_6 in thread 16 | |
26.03.2019 21:43:40 | Process account account_5 in thread 14 | |
26.03.2019 21:43:41 | Process account account_4 in thread 15 | |
26.03.2019 21:43:41 | Process account account_7 locked for time: 26.03.2019 21:45:06 | |
26.03.2019 21:43:41 | Process account account_8 in thread 13 | |
26.03.2019 21:43:41 | Process account account_3 in thread 13 | |
26.03.2019 21:43:42 | Process account account_2 in thread 15 | |
26.03.2019 21:43:44 | Process account account_8 in thread 13 | |
26.03.2019 21:43:44 | Process account account_4 in thread 14 | |
26.03.2019 21:43:44 | Process account account_3 in thread 16 | |
26.03.2019 21:43:45 | Process account account_5 in thread 14 | |
26.03.2019 21:43:46 | Process account account_5 locked for time: 26.03.2019 21:45:29 | |
26.03.2019 21:43:46 | Process account account_6 in thread 14 | |
26.03.2019 21:43:46 | Process account account_4 in thread 15 | |
26.03.2019 21:43:46 | Process account account_2 in thread 14 | |
26.03.2019 21:43:47 | Process account account_6 in thread 16 | |
26.03.2019 21:43:47 | Process account account_3 in thread 16 | |
26.03.2019 21:43:48 | Process account account_8 locked for time: 26.03.2019 21:44:14 | |
26.03.2019 21:43:48 | Process account account_6 in thread 13 | |
26.03.2019 21:43:49 | Process account account_4 in thread 15 | |
26.03.2019 21:43:49 | Process account account_2 in thread 14 | |
26.03.2019 21:43:50 | Process account account_6 in thread 13 | |
26.03.2019 21:43:51 | Process account account_3 locked for time: 26.03.2019 21:45:04 | |
26.03.2019 21:43:51 | Process account account_2 in thread 16 | |
26.03.2019 21:43:53 | Process account account_6 locked for time: 26.03.2019 21:44:00 | |
26.03.2019 21:43:53 | Process account account_4 locked for time: 26.03.2019 21:44:25 | |
26.03.2019 21:43:53 | Process account account_2 in thread 14 | |
26.03.2019 21:43:57 | Process account account_2 in thread 13 | |
26.03.2019 21:43:58 | Process account account_2 in thread 14 | |
26.03.2019 21:44:00 | Process account account_6 in thread 13 | |
26.03.2019 21:44:00 | Process account account_2 in thread 15 | |
26.03.2019 21:44:02 | Process account account_2 in thread 16 | |
26.03.2019 21:44:03 | Process account account_6 in thread 14 | |
26.03.2019 21:44:03 | Process account account_6 in thread 15 | |
26.03.2019 21:44:03 | Process account account_6 in thread 13 | |
26.03.2019 21:44:03 | Process account account_2 in thread 14 | |
26.03.2019 21:44:06 | Process account account_6 in thread 15 | |
26.03.2019 21:44:06 | Process account account_2 in thread 16 | |
26.03.2019 21:44:07 | Process account account_6 in thread 13 | |
26.03.2019 21:44:07 | Process account account_6 in thread 14 | |
26.03.2019 21:44:08 | Process account account_6 in thread 15 | |
26.03.2019 21:44:08 | Process account account_2 in thread 13 | |
26.03.2019 21:44:09 | Process account account_2 in thread 14 | |
26.03.2019 21:44:10 | Process account account_2 in thread 16 | |
26.03.2019 21:44:11 | Process account account_6 in thread 13 | |
26.03.2019 21:44:13 | Process account account_6 in thread 14 | |
26.03.2019 21:44:14 | Process account account_8 in thread 13 | |
26.03.2019 21:44:14 | Process account account_6 in thread 15 | |
26.03.2019 21:44:14 | Process account account_2 in thread 14 | |
26.03.2019 21:44:15 | Process account account_2 locked for time: 26.03.2019 21:44:31 | |
26.03.2019 21:44:17 | Process account account_8 locked for time: 26.03.2019 21:47:10 | |
26.03.2019 21:44:18 | Process account account_6 in thread 16 | |
26.03.2019 21:44:19 | Process account account_6 in thread 13 | |
26.03.2019 21:44:21 | Process account account_6 locked for time: 26.03.2019 21:45:11 | |
26.03.2019 21:44:25 | Process account account_4 in thread 13 | |
26.03.2019 21:44:29 | Process account account_4 in thread 14 | |
26.03.2019 21:44:30 | Process account account_4 in thread 15 | |
26.03.2019 21:44:30 | Process account account_4 in thread 16 | |
26.03.2019 21:44:31 | Process account account_4 in thread 13 | |
26.03.2019 21:44:31 | Process account account_2 in thread 14 | |
26.03.2019 21:44:34 | Process account account_4 in thread 15 | |
26.03.2019 21:44:34 | Process account account_2 in thread 16 | |
26.03.2019 21:44:35 | Process account account_4 in thread 13 | |
26.03.2019 21:44:37 | Process account account_2 in thread 14 | |
26.03.2019 21:44:37 | Process account account_2 in thread 15 | |
26.03.2019 21:44:37 | Process account account_2 in thread 16 | |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System; | |
using System.Collections.Concurrent; | |
using System.Linq; | |
using System.Threading; | |
namespace ConsoleApp1 | |
{ | |
public class Program | |
{ | |
static readonly Random Rng = new Random(); | |
const int WorkerCount = 4; | |
const int AccountCount = 8; | |
public static void Main() | |
{ | |
var cancelSource = new CancellationTokenSource(); | |
var context = new Context | |
{ | |
WaitQueue = new ConcurrentDictionary<string, Account>(), | |
WorkQueue = new ConcurrentQueue<Account>(), | |
Cancel = cancelSource.Token | |
}; | |
for (var i = 0; i < WorkerCount; i++) | |
new Thread(ProcessWorkQueue).Start(context); | |
new Thread(ProcessWaitQueue).Start(context); | |
for (var i = 0; i < AccountCount; i++) | |
{ | |
var id = $"account_{i + 1}"; | |
context.WaitQueue.TryAdd(id, new Account {Id = id}); | |
} | |
Thread.Sleep(60_000); | |
cancelSource.Cancel(); | |
} | |
static void ProcessWaitQueue(object obj) | |
{ | |
var context = (Context) obj; | |
while (!context.Cancel.IsCancellationRequested) | |
{ | |
var ids = context.WaitQueue.Values | |
.Where(a => a.AvailableFrom < DateTime.Now) | |
.OrderBy(x => x.LastActivity) | |
.Select(x => x.Id) | |
.ToList(); | |
if (!ids.Any()) | |
Thread.Sleep(100); | |
foreach (var id in ids) | |
if (context.WaitQueue.TryRemove(id, out var account)) | |
context.WorkQueue.Enqueue(account); | |
} | |
} | |
static void ProcessWorkQueue(object obj) | |
{ | |
var context = (Context) obj; | |
Console.WriteLine("{0} | Begin thread {1}", DateTime.Now, Thread.CurrentThread.ManagedThreadId); | |
while (!context.Cancel.IsCancellationRequested) | |
{ | |
if (context.WorkQueue.TryDequeue(out var account)) | |
{ | |
Console.WriteLine("{0} | Process account {1} in thread {2}", DateTime.Now, account.Id, | |
Thread.CurrentThread.ManagedThreadId); | |
Thread.Sleep(Rng.Next(0, 5) * 1000); | |
if (Rng.Next() % 5 == 0) | |
{ | |
account.AvailableFrom = DateTime.Now.AddSeconds(Rng.Next(0, 200)); | |
Console.WriteLine("{0} | Process account {1} locked for time: {2}", DateTime.Now, account.Id, | |
account.AvailableFrom); | |
} | |
account.LastActivity = DateTime.Now; | |
if (!context.WaitQueue.TryAdd(account.Id, account)) | |
throw new InvalidOperationException("conflict"); | |
} | |
else | |
{ | |
Thread.Sleep(100); | |
} | |
} | |
Console.WriteLine("{0} | End thread {1}", DateTime.Now, Thread.CurrentThread.ManagedThreadId); | |
} | |
} | |
class Context | |
{ | |
public ConcurrentQueue<Account> WorkQueue { get; set; } | |
public ConcurrentDictionary<string, Account> WaitQueue { get; set; } | |
public CancellationToken Cancel { get; set; } | |
} | |
class Account | |
{ | |
public string Id { get; set; } | |
public DateTime AvailableFrom { get; set; } = DateTime.MinValue; | |
public DateTime LastActivity { get; set; } = DateTime.MinValue; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment