Logger之Logger.getLogger(CLass)使用

 以前一直在使用System.out.println()來調試.可是用這種方式開發項目部署到生產環境,會由於衆多的控制檯輸出下降應用的性能.這時候Log4J就成爲可平衡開發和部署應用的利器了.java

  在項目中使用Log4J並非一件困難的事情,簡單粗暴的方式就是在每一個類A中聲明一個Logger私有屬性apache

private static Logger logger = Logger.getLogger(A.class);

這樣雖然簡單,可是帶來有兩個問題:app

 1.增長系統開銷-每一個使用Log4J的類都增長了對象屬性.性能

 2.麻煩:每一個使用Logger的類都要重複聲明上面Logger對象.測試

其實不難發現可使用重構手法,聲明一個公用的類Log4jUtils,處理Logger的公共操做.spa

不過呢,問題不這麼簡單.首先要解決一個問題,Logger.getLogger(A.class)中的A.class有什麼用?A.class能夠不能夠瞎寫?debug

先作個試驗,先簡單配置log4j.properties文件調試

#日誌級別,輸出目的地
log4j.rootLogger=debug,stdout

log4j.appender.stdout=org.apache.log4j.Conso
leAppender
log4j.appender.stdout.Target=System.out
log4j.appender.stdout.layout=org.apache.log4j.PatternLayout

輸出格式

log4j.appender.stdout.layout.ConversionPattern=%c %d{ABSOLUTE} %5p %c{1}:%L - %m%n日誌

測試類code

import org.apache.log4j.Logger;

/**
 * Created by li on 2015/5/24.
 */

public class LoggerTest {
    private static Logger logger = Logger.getLogger(Object.class);

    public static void main(String[] args) {
        logger.debug("Hello World!");
    }
}

查看結果:

結合log4j.properties配置的

log4j.appender.stdout.layout.ConversionPattern=%c %d{ABSOLUTE} %5p %c{1}:%L - %m%n

不難知道%c輸出所屬的類目,一般就是所在類的全名。可是咱們追蹤的實際上是LoggerTest類,結果返回的倒是java.lang.Object,簡直就是誤導(雖然能夠瞎寫,可是不建議,由於咱們可能須要知道輸入日誌的類是哪一個).

這時候將LoggerTest類的代碼修改

private static Logger logger = Logger.getLogger(LoggerTest.class);

運行結果變爲:

要的結果終於出現了.至此,明白了getLogger(class)的參數用途:追蹤產生此日誌的類.

如今就出現了新的問題:若要使用一個類Log4jUtils來專門處理Logger對象的聲明等操做,那麼如何處理getLogger(class)的參數問題?

也就是如何在Log4jUtils獲得調用logger對象的類型.

 

解決這個困難能夠是使用Java的反射機制

看下面的代碼:

/**
 * Created by li on 2015/5/23.
 */
public class Log4JUtils{

    private static Logger logger =  null;

    public static Logger getLogger(){
       if (null == logger){
           //Java8 廢棄了Reflection.getCallerClass()
           logger = Logger.getLogger(Reflection.getCallerClass().getName());
           logger.debug("調用者類名"+Reflection.getCallerClass().getName());
       }
        return logger;
    }
}

 

修改類LoggerTest的代碼:

/**
 * Created by li on 2015/5/24.
 */

public class LoggerTest {
//    private static Logger logger = Logger.getLogger(LoggerTest.class);

    public static void main(String[] args) {
        Log4JUtils.getLogger().debug("Hello World!");
    }
}

 

運行結果:

看到這個結果就很爽了.之後項目就能夠放棄使用System.out.println()打印語句了.

 

log4j中的Logger.getLogger()能夠不用加載一個類,也能夠傳字符串的,這是一種通用作法,好比

Logger logger = Logger.getLogger("com.MyLog");
logger.info("...");
那麼Logger首先會去找log4j.properties中的log4j.category.com.MyLog對應的Appender來寫日誌,固然若是你配置了rootAppender的話不用配其餘的Appender也不要緊。

示例:

/**
 * @Author xiayuxuanmin
 * @Date 2019/8/10
 * @Description
 */
public class LoggerTest {
    private static Logger logger = Logger.getLogger("myLog");

    public static void main(String[] args) {
        logger.info("我是日誌");
    }
}

控制檯輸出:

由上可知:能夠直接在getLogger()方法中傳入一個string類型的字符串,那麼就能夠省去類的開銷(這裏也能夠瞎寫的,可是最好和當前類保持一致,這樣在看日誌的時候能夠知道是哪一個類產生的日誌...)

相關文章
相關標籤/搜索