代码改变世界

异步处理队列(简单实用)

2012-11-13 18:02  Simon.Jiang  阅读(789)  评论(0编辑  收藏  举报

异步处理接口

/// <summary>
    /// 异步处理接口
    /// </summary>
    public interface IAsyncHandle
    {
        /// <summary>
        /// 异步处理参数
        /// </summary>
        IHandleArgs AsyncHandleParameter { get; set; }

        /// <summary>
        /// 异步处理调用方法
        /// </summary>
        /// <param name="param"></param>
        /// <returns></returns>
        object Handle(IHandleArgs param);
    }
    /// <summary>
    /// 异步队列参数
    /// </summary>
    public interface IHandleArgs
    {
        /// <summary>
        /// 名称
        /// </summary>
        string Name { get; set; }
    }

异步管理类:

    /// <summary>
    /// 异步队列管理类
    /// </summary>
    public class AsyncQueue
    {
        /// <summary>
        /// 线程列表,保持线程引用,不被清除
        /// </summary>
        private static List<Thread> threadList = null;

        /// <summary>
        /// 操作队列
        /// </summary>
        private static Queue handleQueue = null;

        static AsyncQueue()
        {
            //初始化队列
            handleQueue = new Queue();
            //初始化处理线程列表
            threadList = new List<Thread>();
            for (int i = 0; i < 2; i++)
            {
                Thread t = new Thread(new ThreadStart(AsyncProcess));
                threadList.Add(t);
            }
            //启动处理线程
            foreach (Thread t in threadList)
            {
                t.Start();
            }
        }

        static void AsyncProcess()
        {
            while (true)
            {
                IAsyncHandle asyncHandle = DeQueue();
                try
                {
                    if (asyncHandle == null)
                    {
                        return;
                    }
                    asyncHandle.Handle(asyncHandle.AsyncHandleParameter);
                }
                catch (Exception ex)
                { 
                    //...
                }
            }
        }

        /// <summary>
        /// 入队
        /// </summary>
        /// <param name="asyncEntity"></param>
        public static void EnQueue(IAsyncHandle asyncEntity)
        {
            lock (handleQueue)
            {
                handleQueue.Enqueue(asyncEntity);
            }
        }

        /// <summary>
        /// 出对
        /// </summary>
        /// <returns></returns>
        static IAsyncHandle DeQueue()
        {
            object obj = null;
            lock (handleQueue)
            {
                if (handleQueue.Count > 0)
                {
                    obj = handleQueue.Dequeue();
                }
            }
            if (obj == null)
            {
                return null;
            }
            return (IAsyncHandle)obj;
        }
    }

一个简单的队列封装凭借上面2个接口或者类就可以了,那么下面做一个测试。比如需要做异步日志处理,如下:

    /// <summary>
    /// 日志处理参数实体类
    /// </summary>
    public class LogHandleArgs : IHandleArgs
    {
        /// <summary>
        /// 日志名称
        /// </summary>
        public string LogName { get; set; }

        private string m_Name;
        /// <summary>
        /// 基类参数
        /// </summary>
        public string Name
        {
            get
            {
                return this.m_Name;
            }
            set
            {
                this.m_Name = value;
            }
        }
    }
    /// <summary>
    /// 日志异步处理
    /// </summary>
    public class LogAsyncHandle : IAsyncHandle
    {
        private LogHandleArgs m_LogHandleArgs;
        /// <summary>
        /// 日志参数
        /// </summary>
        public IHandleArgs AsyncHandleParameter
        {
            get
            {
                return this.m_LogHandleArgs;
            }
            set
            {
                this.m_LogHandleArgs = (LogHandleArgs)value;
            }
        }

        /// <summary>
        /// 日志处理
        /// </summary>
        /// <param name="param"></param>
        /// <returns></returns>
        public object Handle(IHandleArgs param)
        {
            LogHandleArgs ar = (LogHandleArgs)param;
            Console.WriteLine("Log...Name={0}", ar.Name);
            return null;
        }
    }

通过继承来实现自己的业务,当然你也可以实现其他业务。

最后来进行下测试:

    class Program
    {
        static void Main(string[] args)
        {
            for (int i = 0; i < 10; i++)
            {
                LogAsyncHandle handle = new LogAsyncHandle();
                LogHandleArgs arg = new LogHandleArgs();
                arg.LogName = "Simon" + i.ToString();
                arg.Name = "test" + i.ToString();
                handle.AsyncHandleParameter = arg;

                AsyncQueue.EnQueue(handle);
            }
            Console.ReadLine();
        }
    }

那么测试结果给大家看下: