zoukankan      html  css  js  c++  java
  • 一个简单的Log类

    经常在运行程序时需要在某些地方记录log,之前想用Log4Net,但又感觉要附带一个dll,想要只带一个exe文件运行,干脆自己写个简单的类了。

    需要满足的条件:被多个线程调用;时间的准确性不重要,知道先后关系就行;不想阻塞线程,毕竟干活才是主要目的,为了不太在意时间的log而阻塞等待有点不划算。

    然后开始:1.需要静态类,默认存储在当前目录下,可指定log文件名;2.需要一个用来写入到文件的方法。

    public static class LogWriter
    {
       static string logPath ="Log_"+ DateTime.Now.ToString("yyyyMMdd") + ".txt";    
       private static void WriteLine_Helper(string str)
            {
                using (System.IO.StreamWriter writer = new System.IO.StreamWriter(logPath, true))
                {
                    writer.WriteLine(DateTime.Now.ToString("yyyy/MM/dd  HH:mm:ss    ") + str);
                    writer.Close();
                }
            }
    }

    然后,直接写的话会存在同时访问的问题,在不使用锁进行阻塞的前提下,这里使用两个List存储消息队列,并用一个bool变量UseList1来标识当前存储到的List,当存储List1的时候,建立线程将List2中的内容写入到log并清除list2中的消息,然后取反UseList1,将消息存储到List2队列,此时将List1中的消息写入log并清除list1中的消息,最后检查list1和list2中是否还有消息,如果有则继续写入。

    static List<string> list1 = new List<string>();
    static List<string> list2 = new List<string>();
    static bool UseList1 = false;
    static bool isUsed = false;
    
    public static void WriteLine(string str)     //将消息放进List中
            {
                if (UseList1)    //如果当前正在使用List1写入log,就将消息放入list2
                {
                    list2.Add(str);
                }
                else
                {
                    list1.Add(str);
                }
    
                if (!isUsed)    //如果没开启线程,则开启线程
                {
                    isUsed = true;
                    Thread t = new Thread(WriteList);
                    t.Start();
                }
            }
    private static void WriteList()   //将list中的消息写入log
            {
                if (UseList1)   //如果正在使用list1,则将list1的消息写入log
                {
                    Write(list1);
                    list1.Clear();  //list1的消息写入完成后清除list1消息
                    UseList1 = false;   //取反UseList1,之后消息写入List2
                    Write(list2);   //将list2中的消息写入log
                    list2.Clear();   //清除list2中的消息
                }
                else
                {
                    Write(list2);
                    list2.Clear();
                    UseList1 = true;
                    Write(list1);
                    list1.Clear();
                }
                isClear();   //检查在写入log期间是否有新增消息,如果有则继续写
                isUsed = false;
            }
    
    private static void Write(List<string> list)   //将list中的消息写入log文件
            {
                for (int i = 0; i < list.Count; i++)
                {
                    WriteLine_Helper(list[i]);
                }
            }
    
    public static void isClear()   //检查是否list1和list2中是否还有消息未写入
            {
                if (list1.Count>0 || list2.Count>0)
                {
                    WriteList();
                }
            }

    实践发现写log频率高的时候的确log消息会滞后几秒,应该是频繁建立线程和频繁的打开和关闭文件造成的。可以建立一个线程等待消息,增加一个list计数,当list中消息达到一定数量的时候再打开文件写入log,减少文件的打开和操作次数,不过对于只是偶尔看看状态用的log,不折腾了。。。

  • 相关阅读:
    Parcel与Parcelable剖析
    Binder文集
    Charles 使用教程
    AsyncTask
    Android 编译时注解
    scanf(),gets(),getchar()
    银行家算法
    最长公共子序列(LCS)问题
    动态规划 求解数字三角形最大值
    参数 存在二维数组
  • 原文地址:https://www.cnblogs.com/Elvis-Luo/p/11470538.html
Copyright © 2011-2022 走看看