2013-05-12 52 views
1

由於下面的類Log4jImpl,我想知道它的'初始化(類初始化不是對象),是否會導致org.apache.log4j.Levelorg.apache.log4j.Logger被初始化?類初始化檢查它的成員方法嗎?


import org.apache.log4j.Level; 
import org.apache.log4j.Logger; 

public class Log4jImpl{ 

    private static final String FQCN = Log4jImpl.class.getName(); 

    private Logger log; 

    public Log4jImpl(String clazz) { 
    log = Logger.getLogger(clazz); 
    } 

    public boolean isDebugEnabled() { 
    return log.isDebugEnabled(); 
    } 

    public boolean isTraceEnabled() { 
    return log.isTraceEnabled(); 
    } 

    public void error(String s, Throwable e) { 
    log.log(FQCN, Level.ERROR, s, e); 
    } 

    public void error(String s) { 
    log.log(FQCN, Level.ERROR, s, null); 
    } 

    public void debug(String s) { 
    log.log(FQCN, Level.DEBUG, s, null); 
    } 

    public void trace(String s) { 
    log.log(FQCN, Level.TRACE, s, null); 
    } 

    public void warn(String s) { 
    log.log(FQCN, Level.WARN, s, null); 
    } 

} 

回答

1

Logger類的Intialization會發生的實現:在Log4jImpl構造。 Level類的初始化時會發生調用它的靜態字段之一:Level.ERRORLevel.DEBUG ...

當類初始化的Java language specs時見。

interface I { 
    public static final int i = 1, ii = Test10.out("ii", 2), kk = Test10.out("kk", 3); 
} 
interface J extends I { 
    int j = Test10.out("j", 3), jj = Test10.out("jj", 4); 
} 
interface K extends J { 
    int k = Test10.out("k", 5); 
} 
class Test10 { 
    public static void main(String[] args) { 
     System.out.println(J.ii); 
     System.out.println(K.j); 
    } 
    static int out(String s, int i) { 
     System.out.println(s + "=" + i); 
     return i; 
    } 
} 
+0

從「specs」中,我看到「使用T聲明的靜態字段並且該字段不是常量變量」。但是Level.ERROR,Level.DEBUG等是「public static final」字段。如何解釋? – duanjfeng 2013-05-12 12:01:52

+0

@duanjfeng是的,但是如果你看源代碼,常量初始化爲:'public static final ERROR = new Level()' – dcernahoschi 2013-05-12 14:54:16

+0

你的意思是Log4jImpl類嘗試解析這些常量,但它們是class Level,讓jvm嘗試加載類Level? (你會告訴我更多的官方參考,我可以讀到這個?) – duanjfeng 2013-05-12 15:10:11

1

使用Log4jImpl.class將不會加載任何其他類。當你在構造函數中使用它們時,它們會被加載。

BTW通常XxxxImpl意味着你有一個接口調用它的靜態方法getLogger當XXXX

+0

但實際上,當我調用Class.forName(Log4jImpl.class.getName())時,類加載器嘗試加載org.apache.log4j.Level。 – duanjfeng 2013-05-12 11:57:32

+0

'Log4jImpl.class'觸發要加載的類。你想要'Class.forName(「Log4jImpl」,false,null);' – 2013-05-12 13:02:29

+0

爲什麼Log4jImpl觸發? Level.ERROR,Level.DEBUG等是「公共靜態最終」字段。 – duanjfeng 2013-05-12 14:43:15