{"id":5271,"date":"2021-09-03T13:44:09","date_gmt":"2021-09-03T12:44:09","guid":{"rendered":"https:\/\/solidt.eu\/site\/?p=5271"},"modified":"2022-07-25T08:31:28","modified_gmt":"2022-07-25T07:31:28","slug":"c-debounced-process-queue","status":"publish","type":"post","link":"https:\/\/solidt.eu\/site\/c-debounced-process-queue\/","title":{"rendered":"C# Debounced Process Queue"},"content":{"rendered":"\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"csharp\" data-enlighter-theme=\"\" data-enlighter-highlight=\"\" data-enlighter-linenumbers=\"\" data-enlighter-lineoffset=\"\" data-enlighter-title=\"\" data-enlighter-group=\"\">public class DebouncedProcessQueue&lt;T>\n{\n\tprivate readonly ConcurrentQueue&lt;T> queue = new ConcurrentQueue&lt;T>();\n\tprivate readonly Debouncer debouncer;\n\tprivate readonly Action&lt;IEnumerable&lt;T>> processAction;\n\tprivate readonly int flushAfterQueueCount;\n\tpublic DebouncedProcessQueue(Action&lt;IEnumerable&lt;T>> processAction, TimeSpan debounceTime, int flushAfterQueueCount = 50)\n\t{\n\t\tdebouncer = new Debouncer(debounceTime, ProcessQueue);\n\t\tthis.processAction = processAction;\n\t\tthis.flushAfterQueueCount = flushAfterQueueCount;\n\t}\n\tprivate void ProcessQueue()\n\t{\n\t\tvar items = new List&lt;T>();\n\t\twhile (!queue.IsEmpty)\n\t\t{\n\t\t\tif (queue.TryDequeue(out var item))\n\t\t\t\titems.Add(item);\n\t\t}\n\t\tif (items.Count == 0) return;\n\t\tprocessAction(items);\n\t}\n\tpublic void Enqueue(T item)\n\t{\n\t\tqueue.Enqueue(item);\n\t\tif (queue.Count > flushAfterQueueCount)\n\t\t\tdebouncer.Flush();\n\t\telse\n\t\t\tdebouncer.Debounce();\n\t}\n\n\tpublic void Flush() => debouncer.Flush();\n}\n\npublic class Debouncer\n{\n\tpublic Debouncer(TimeSpan interval, Action action)\n\t{\n\t\t_interval = interval;\n\t\t_action = action;\n\t}\n\tprivate volatile Timer _timer;\n\tprivate readonly TimeSpan _interval;\n\tprivate readonly Action _action;\n\n\tpublic void Debounce()\n\t{\n\t\t_timer?.Dispose();\n\t\t_timer = new Timer((state) =>\n\t\t{\n\t\t\t_action?.Invoke();\n\t\t\t_timer?.Dispose();\n\t\t}, null, (int)_interval.TotalMilliseconds, -1);\n\t}\n\n\tpublic void Flush()\n\t{\n\t\t_timer?.Dispose();\n\t\t_action?.Invoke();\n\t}\n}<\/pre>\n","protected":false},"excerpt":{"rendered":"","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"inline_featured_image":false,"footnotes":""},"categories":[6,4,1],"tags":[],"class_list":["post-5271","post","type-post","status-publish","format-standard","hentry","category-dotnet","category-programming","category-uncategorized"],"_links":{"self":[{"href":"https:\/\/solidt.eu\/site\/wp-json\/wp\/v2\/posts\/5271","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/solidt.eu\/site\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/solidt.eu\/site\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/solidt.eu\/site\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/solidt.eu\/site\/wp-json\/wp\/v2\/comments?post=5271"}],"version-history":[{"count":4,"href":"https:\/\/solidt.eu\/site\/wp-json\/wp\/v2\/posts\/5271\/revisions"}],"predecessor-version":[{"id":6128,"href":"https:\/\/solidt.eu\/site\/wp-json\/wp\/v2\/posts\/5271\/revisions\/6128"}],"wp:attachment":[{"href":"https:\/\/solidt.eu\/site\/wp-json\/wp\/v2\/media?parent=5271"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/solidt.eu\/site\/wp-json\/wp\/v2\/categories?post=5271"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/solidt.eu\/site\/wp-json\/wp\/v2\/tags?post=5271"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}