Log工具 C++面向對象設計

       自己設計了一個小的Log工具,主要是想加強下自己linux下的編碼能力,及程序的設計能力。

       希望有共同目標的同學一起討論下,大家一起多弄些小的實例,共同討論下,增強下程序設計方面的知識、經驗。

-------------------------------

Log使用說明:

       日誌記錄項說明:
                 2012-11-23 11:50:50 [12257 : 12257] [main.cpp : int main(int, char**)] :hahhaha
                      日期       時間      進程號   線程號   文件名               函數名               自定義消息
  


    使用方式:

        創建:
        WYKLog* logStdOut = LogStdOut::getLogStdOut();   //屏幕輸出  綠色
        WYKLog* logStdErr = LogStdErr::getLogStdErr();   //屏幕輸出  紅色
        WYKLog* logStdFile = LogFile::getLogFile(dir, filePreFix, 10);   
                // 記錄到日誌文件, 文件名 “filePreFix2012-11-23.log"  前綴+日期.log
                // 文件存放到dir指定目錄下
                // 每隔10天生成一個新的日誌文件
        WYKLog* logStdFile = LogFile::getLogFile();
                // 默認創建 "./log-dir"文件夾
                // 文件沒有前綴 "日期.log"
                // 每隔7天生成一個新的日誌文件
        記錄:
        logXXX->m_log("自己的消息");  

---------------------------------------

源碼:

      log.h 文件:

#ifndef _LOG_H_
#define _LOG_H_
/*====================================================================
*
* 功能 : 
*
* 作者 : WYK
*
* 日期 : 2012年11月22日 星期四 11時49分33秒
*
====================================================================*/

#include <sys/types.h>
#include <stdio.h>
#include <string>

#define m_log(msg) log(__FILE__, __PRETTY_FUNCTION__, msg)

class WYKLog
{
    public:
        bool log(const char* file, const char* func,const char* msg);
    
    protected:
        WYKLog();
        virtual bool record(const char* tip,const char* msg) = 0;
        
    private:
        WYKLog(WYKLog&);
        WYKLog& operator=(WYKLog&);
        
    private:
        pid_t pid;
};

class LogStdOut: public WYKLog
{
    public:
        static LogStdOut* getLogStdOut();
        
    protected:
        bool record(const char* tip, const char* msg);
        
    private:
        LogStdOut(){};
        ~LogStdOut(){};
        LogStdOut(LogStdOut&){};
        LogStdOut& operator=(LogStdOut&){};
        
    private:
        static LogStdOut* singleInstance;
};

class LogStdErr: public WYKLog
{
    public:
        static LogStdErr* getLogStdErr();
        
    protected:
        bool record(const char* tip, const char* msg);
        
    private:
        LogStdErr(){};
        ~LogStdErr(){};
        LogStdErr(LogStdErr&){};
        LogStdErr& operator=(LogStdErr&){};
        
    private:
        static LogStdErr* singleInstance;
};

class LogFile: public WYKLog
{
    public:
        static LogFile* getLogFile(const char* dir, const char* _preFix, int _day = 7);
        static LogFile* getLogFile();
        ~LogFile();
    
    protected:
        bool record(const char* tip, const char* msg);
    private:
        LogFile(const char* dir, const char* _preFix, int _day);
        bool greaterTimeSeg();
        bool newLogFile();
        void closeLogFile();
        
        LogFile(LogFile&);
        LogFile& operator=(LogFile&);
    
    private:
        FILE* file;
        time_t start;
        static LogFile* singleInstance;
        
        std::string preFix;
        int preFixLen;
        int timeSeg;

};

#endif

logStdErr.cpp文件

/*===================================================================
*
* 功能 : 
*
* 作者 : WYK
*
* 日期 : 2012年11月23日 星期五 09時57分28秒
*
===================================================================*/

#include "log.h"
#include <stdio.h>
#include <string>

LogStdErr* LogStdErr::singleInstance = NULL;

LogStdErr* LogStdErr::getLogStdErr()
{
    if(NULL == singleInstance)
    {
        try{singleInstance = new LogStdErr();}
        catch(std::bad_alloc e)
        {
            printf("\033[31m new LogStdErr error\033[0m\n");
            return NULL;
        }
    }
    return singleInstance;
}

bool LogStdErr::record(const char* tip, const char* msg)
{
    if(NULL == msg)
        printf("\033[31m %s \033[0m\n", tip);
    else
        printf("\033[31m %s %s \033[0m\n",tip, msg);
    
    return true;
}
////////////////////////////////////////////////////////////////////
// END

logStdOut.cpp文件

/*===================================================================
*
* 功能 : 
*
* 作者 : WYK
*
* 日期 : 2012年11月22日 星期四 11時50分45秒
*
===================================================================*/

#include "log.h"
#include <stdio.h>
#include <string>

LogStdOut* LogStdOut::singleInstance = NULL;

LogStdOut* LogStdOut::getLogStdOut()
{
    if(NULL == singleInstance)
    {
        try{singleInstance = new LogStdOut();}
        catch(std::bad_alloc e)
        {
            printf("\033[31m new LogStdOut error\033[0m\n");
            return NULL;
        }
    }
    return singleInstance;
}

bool LogStdOut::record(const char* tip, const char* msg)
{
    if(NULL == msg)
        printf("\033[32m %s \033[0m\n", tip);
    else
        printf("\033[32m %s %s \033[0m\n",tip, msg);
    
    return true;
}

////////////////////////////////////////////////////////////////////
// END

logFile.cpp文件
/*===================================================================
*
* 功能 : 
*
* 作者 : WYK
*
* 日期 : 2012年11月22日 星期四 11時50分31秒
*
===================================================================*/

#include <sys/stat.h>
#include <sys/types.h>
#include <dirent.h>
#include "log.h"

const int DAY_SEC = 24*3600;

LogFile* LogFile::singleInstance = NULL;

LogFile* LogFile::getLogFile(const char* dir, const char* _preFix, int _day)
{
    if(NULL == singleInstance)
    {
        try{singleInstance = new LogFile(dir, _preFix, _day);}
        catch(std::bad_alloc e)
        {
            printf("\033[31m new LogFile error \033[0m\n");
            return NULL;
        }
        catch(int e)
        {
            return NULL;
        }
    }
    return singleInstance;
}

LogFile* LogFile::getLogFile()
{
    if(NULL == singleInstance)
    {
        try{singleInstance = new LogFile(NULL, NULL, 7);}
        catch(std::bad_alloc e)
        {
            printf("\033[31m new LogFile error \033[0m\n");
            return NULL;
        }
        catch(int e)
        {
            return NULL;
        }
    }
    return singleInstance;
}

LogFile::LogFile(const char* dir, const char* _preFix, int _day):file(NULL),start(0)
{
    if(NULL == dir || 0 == *dir)
    {
        dir = "./log-dir";
    }
    if(-1 == access(dir, 0))
    {
        if(mkdir(dir, 0777))
        {
            printf("\033[31m make dir error\033[0m\n");
            throw (-1);
        }
    }
    else 
    {
        DIR* dp;
        if(NULL == (dp=opendir(dir)))
        {
            printf("\033[31m dirName exits, but not dir error\033[0m\n");
            throw (-2);
        }
        else
            closedir(dp);
    }
   
    preFix = dir;
    if('/' != dir[strlen(dir)-1])
    {
        preFix += "/";
    }
    
    if(NULL != _preFix)
    {
        preFix += _preFix;
    }
    preFixLen = preFix.length();

    if(_day > 30)
        _day = 30;
    timeSeg = DAY_SEC * _day;
}

LogFile::~LogFile()
{
    closeLogFile();
}

bool LogFile::record(const char* tip, const char* msg)
{
    if(greaterTimeSeg())
        newLogFile();
        
    fwrite(tip, strlen(tip), 1, file);
    fwrite(msg, strlen(msg), 1, file);
    fwrite("\n", 1, 1, file);
    return true;
}

bool LogFile::greaterTimeSeg()
{
    time_t now;
    time(&now);
    if(now-start > timeSeg)
    {
        start = now;
        return true;
    }
    else
    {
        return false;
    }
}


bool LogFile::newLogFile()
{
    char fileName[256];
    strcpy(fileName, preFix.c_str());

    time_t now;
    time(&now);
    strftime(fileName+preFixLen, 20, "_%Y-%m-%d.log", localtime(&now));
    
    closeLogFile();
    file = fopen(fileName, "w");
    if(NULL == file)
        return false;
    else 
        return true;
}

void LogFile::closeLogFile()
{
    if(NULL != file)
    {
        fclose(file);
        file = NULL;
    }
}

////////////////////////////////////////////////////////////////////
// END

test.cpp

/*===================================================================
*
* 功能 : 
*
* 作者 : WYK
*
* 日期 : 2012年11月22日 星期四 15時09分59秒
*
===================================================================*/

#include "log.h"
#include <stdio.h>
#include <pthread.h>

//g++ -g log.cpp logStdOut.cpp logStdErr.cpp logFile.cpp main.cpp -o log
//g++ -g main.cpp liblog.a -L/usr/lib/ntpl -lpthread -o log

WYKLog* logOut = NULL;
WYKLog* logErr = NULL;
WYKLog* logFile = NULL;

void* threadFunc(void* arg);

int main(int argc, char** argv)
{
    logOut = LogStdOut::getLogStdOut();
    if(NULL == logOut)
    {
        printf("logOut get error\n");
        exit(1);
    }
    
    logOut->m_log("stdout : kkkkkkkkk");
    
    logErr = LogStdErr::getLogStdErr();
    if(NULL == logErr)
    {
        printf("logErr get error\n");
        exit(1);
    }
    
    logErr->m_log("stderr : llllllllll");

    logFile = LogFile::getLogFile("./log-dir", "test", 7);
    if(NULL == logFile)
    {
        printf("logFile get error\n");
        exit(1);
    }
    
    pthread_t thread1;
    int ret = pthread_create(&thread1, NULL, threadFunc, NULL);
    if(0 != ret)
    {
        printf("create thread error\n");
        exit(1);
    }
    
    
    int i = 0;
    while(i++ < 10)
    {
        logOut->m_log("stdout : kkkkkkkkk");
        logErr->m_log("stderr : lllllllll");
        logFile->m_log("hahhaha");
        usleep(5*1000000);
    }
    return 0;
}

void* threadFunc(void* arg)
{
    printf("====in child thread===\n");
    int i = 0;
    while(i++ < 5)
    {
        printf("====go child thread===\n");
        logFile->m_log("abcdefghi");
        usleep(10*1000000);
    }
}
////////////////////////////////////////////////////////////////////
// END

有設計不合理的地方,希望大家指點下,萬分感謝!

發佈了38 篇原創文章 · 獲贊 1 · 訪問量 7萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章