zoukankan      html  css  js  c++  java
  • C# ThreadContextPool 对象池

    public class ThreadContextPool<T> where T : class
    {
    #region NestedType
    private struct Entry
    {
    public int ThreadID;
    public T Value;
    }

    private struct PendingEntry
    {
    public int ThreadID;
    public int ReturnCount;
    }

    private class GlobalPool
    {
    private int maxCount;
    private Stack<T> items;

    public int MaxCount
    {
    get { return maxCount; }
    set
    {
    lock (items)
    {
    while (items.Count > value)
    {
    items.Pop();
    }
    maxCount
    = value;
    }
    }
    }

    public GlobalPool(int maxCount)
    {
    this.maxCount = maxCount;
    this.items = new Stack<T>();
    }

    public void Clear()
    {
    lock (items)
    {
    items.Clear();
    }
    }

    public void DecrementMaxCount()
    {
    lock (items)
    {
    if (items.Count == maxCount)
    {
    items.Pop();
    }
    maxCount
    --;
    }
    }

    public bool Return(T value)
    {
    if (items.Count < MaxCount)
    {
    lock (items)
    {
    if (items.Count < MaxCount)
    {
    items.Push(value);
    return true;
    }
    }
    }
    return false;
    }

    public T Take()
    {
    if (items.Count > 0)
    {
    lock (items)
    {
    if (items.Count > 0)
    {
    return items.Pop();
    }
    }
    }
    return null;
    }
    }
    #endregion

    #region Fields
    private const int maxPendingEntries = 128;
    private const int maxPromotionFailures = 64;
    private const int maxReturnsBeforePromotion = 64;
    private const int maxThreadItemsPerProcessor = 16;
    private int maxCount, promotionFailures;
    private Entry[] entries;
    private PendingEntry[] pending;
    private GlobalPool globalPool;
    #endregion

    #region Properties
    public int MinSize
    {
    get { return 0; }
    }
    public int MaxSize
    {
    get { return maxCount; }
    }
    public int Size
    {
    get { throw new NotSupportedException(); }
    }
    #endregion

    #region Methods
    public ThreadContextPool(int maxCount)
    {
    int num = maxCount;
    int num2 = maxThreadItemsPerProcessor + Environment.ProcessorCount;
    if (num > num2)
    {
    num
    = num2;
    }
    this.maxCount = maxCount;
    this.entries = new Entry[num];
    this.pending = new PendingEntry[4];
    this.globalPool = new GlobalPool(maxCount);
    }

    public void Clear()
    {
    for (int i = 0; i < entries.Length; i++)
    {
    entries[i].Value
    = null;
    }
    globalPool.Clear();
    }

    public bool Return(T item)
    {
    int managedThreadId = Thread.CurrentThread.ManagedThreadId;
    if (managedThreadId == 0)
    {
    return false;
    }
    bool flag = ReturnToPerThreadPool(managedThreadId, item);
    if (!flag)
    {
    RecordReturnToGlobalPool(managedThreadId);
    flag
    = globalPool.Return(item);
    }
    return flag;
    }

    private bool ReturnToPerThreadPool(int thisThreadID, T value)
    {
    for (int i = 0; i < entries.Length; i++)
    {
    int threadID = entries[i].ThreadID;
    if (threadID == thisThreadID)
    {
    if (entries[i].Value == null)
    {
    entries[i].Value
    = value;
    return true;
    }
    return false;
    }
    if (threadID == 0)
    {
    break;
    }
    }
    return false;
    }

    private void RecordReturnToGlobalPool(int thisThreadID)
    {
    for (int i = 0; i < pending.Length; i++)
    {
    int threadID = pending[i].ThreadID;
    if (threadID == thisThreadID)
    {
    int num3 = pending[i].ReturnCount + 1;
    if (num3 < maxReturnsBeforePromotion)
    {
    pending[i].ReturnCount
    = num3;
    return;
    }
    pending[i].ReturnCount
    = 0;
    if (!PromoteThread(thisThreadID))
    {
    HandlePromotionFailure(thisThreadID);
    return;
    }
    break;
    }
    if (threadID == 0)
    {
    return;
    }
    }
    }
    private bool PromoteThread(int thisThreadID)
    {
    lock (entries)
    {
    for (int i = 0; i < entries.Length; i++)
    {
    int threadID = entries[i].ThreadID;
    if (threadID == thisThreadID)
    {
    return true;
    }
    if (threadID == 0)
    {
    globalPool.DecrementMaxCount();
    entries[i].ThreadID
    = thisThreadID;
    return true;
    }
    }
    }
    return false;
    }
    private void HandlePromotionFailure(int thisThreadID)
    {
    int num = promotionFailures + 1;
    if (num >= maxPromotionFailures)
    {
    lock (entries)
    {
    entries
    = new Entry[entries.Length];
    globalPool.MaxCount
    = maxCount;
    }
    PromoteThread(thisThreadID);
    }
    else
    {
    promotionFailures
    = num;
    }
    }

    public T Take()
    {
    int managedThreadId = Thread.CurrentThread.ManagedThreadId;
    if (managedThreadId == 0)
    {
    return null;
    }
    T local
    = this.TakeFromPerThreadPool(managedThreadId);
    if (local != null)
    {
    return local;
    }
    this.RecordTakeFromGlobalPool(managedThreadId);
    return globalPool.Take();
    }

    private T TakeFromPerThreadPool(int thisThreadID)
    {
    for (int i = 0; i < entries.Length; i++)
    {
    int threadID = entries[i].ThreadID;
    if (threadID == thisThreadID)
    {
    T local
    = entries[i].Value;
    if (local != null)
    {
    entries[i].Value
    = null;
    return local;
    }
    return null;
    }
    if (threadID == 0)
    {
    break;
    }
    }
    return null;
    }

    private void RecordTakeFromGlobalPool(int thisThreadID)
    {
    for (int i = 0; i < pending.Length; i++)
    {
    int threadID = pending[i].ThreadID;
    if (threadID == thisThreadID)
    {
    return;
    }
    if (threadID == 0)
    {
    lock (pending)
    {
    if (pending[i].ThreadID == 0)
    {
    pending[i].ThreadID
    = thisThreadID;
    return;
    }
    }
    }
    }
    if (pending.Length >= maxPendingEntries)
    {
    this.pending = new PendingEntry[pending.Length];
    }
    else
    {
    PendingEntry[] destinationArray
    = new PendingEntry[pending.Length * 2];
    Array.Copy(pending, destinationArray, pending.Length);
    this.pending = destinationArray;
    }
    }
    #endregion
    }
  • 相关阅读:
    bootstrap-select用法详解
    启动react项目报如下错误
    什么?女朋友生气哄不好?那是你没有这款神器!
    Python竟然能做这种进度条,看完别说WC!
    看完学习Python的萌新都在问的六个问题,你就可以毕业了!
    批量加水印防抄袭,Python轻松搞定!
    hdu_1272_小希的迷宫_201403091527
    hdu_1856_More is better_201403091720
    hdu_1213_How Many Tables_201403091126
    hdu_1232_畅通工程_201403091018
  • 原文地址:https://www.cnblogs.com/Googler/p/1752243.html
Copyright © 2011-2022 走看看