美文网首页云时代架构
Java日志框架性能比较

Java日志框架性能比较

作者: 贾博岩 | 来源:发表于2017-06-18 17:33 被阅读1036次

    1 Java日志框架性能比较

    前面几章,笔者分别介绍了log4j,logback,log4j2三大日志实现框架。

    接下来,就用具体的数据比较下,哪个日志框架的性能更好!

    单线程:外循环100次,内循环100000次;

    多线程:开启100个线程,每个线程执行100000次;

    1.1 测试代码:

    (1)log4j:

    public class log4jDemo {
    
        Logger logger = Logger.getLogger(log4jDemo.class);
    
        @Test
        public void testThread() throws InterruptedException {
            int THREAD_NUM = 100;
            final int LOOP_NUM = 100000;
    
            final CountDownLatch countDownLatch = new CountDownLatch(THREAD_NUM);
            long start = System.currentTimeMillis();
            for(int x= 0;x < THREAD_NUM;x++){
                new Thread(new Runnable() {
                    public void run() {
                        for (int y = 0; y < LOOP_NUM; y++) {
                            logger.info("Info Message!");
                        }
                        countDownLatch.countDown();
                    }
                }).start();
            }
            countDownLatch.await();
            System.out.println(System.currentTimeMillis() - start);
        }
    
        @Test
        public void test() throws InterruptedException {
            int X_NUM = 100;
            int Y_NUM = 100000;
    
            long start = System.currentTimeMillis();
            for(int x=0;x < X_NUM;x++) {
                for (int y = 0; y < Y_NUM; y++) {
                    logger.info("Info Message!");
                }
            }
            System.out.print(System.currentTimeMillis() - start);
        }
    }
    

    (2)logback:

    public class logbackDemo {
    
        Logger logger =  LoggerFactory.getLogger(logbackDemo.class);
    
        @Test
        public void testThread() throws InterruptedException {
            int THREAD_NUM = 100;
            final int LOOP_NUM = 100000;
    
            final CountDownLatch countDownLatch = new CountDownLatch(THREAD_NUM);
            long start = System.currentTimeMillis();
            for(int x= 0;x < THREAD_NUM;x++){
                new Thread(new Runnable() {
                    public void run() {
                        for (int y = 0; y < LOOP_NUM; y++) {
                            logger.info("Info Message!");
                        }
                        countDownLatch.countDown();
                    }
                }).start();
            }
            countDownLatch.await();
            System.out.println(System.currentTimeMillis() - start);
        }
    
        @Test
        public void test() {
            int X_NUM = 100;
            int Y_NUM = 100000;
    
            long start = System.currentTimeMillis();
            for(int x=0;x<X_NUM;x++) {
                for (int y = 0; y < Y_NUM; y++) {
                    logger.info("Info Message!");
                }
            }
            System.out.print(System.currentTimeMillis()-start);
        }
    }
    

    (3)log4j2:

    public class log4j2Demo {
        private Logger logger = LogManager.getLogger(log4j2Demo.class);
    
        @Test
        public void testThread() throws InterruptedException {
            int THREAD_NUM = 100;
            final int LOOP_NUM = 100000;
    
            final CountDownLatch countDownLatch = new CountDownLatch(THREAD_NUM);
            long start = System.currentTimeMillis();
            for(int x= 0;x < THREAD_NUM;x++){
                new Thread(new Runnable() {
                    public void run() {
                        for (int y = 0; y < LOOP_NUM; y++) {
                            logger.info("Info Message!");
                        }
                        countDownLatch.countDown();
                    }
                }).start();
            }
            countDownLatch.await();
            System.out.println(System.currentTimeMillis() - start);
        }
        
        @Test
        public void test() throws InterruptedException {
            int X_NUM = 100;
            int Y_NUM = 100000;
    
            long start = System.currentTimeMillis();
            for(int x=0;x<X_NUM;x++) {
                for (int y = 0; y < Y_NUM; y++) {
                    logger.info("Info Message!");
                }
            }
            System.out.print(System.currentTimeMillis() - start);
        }
    }
    

    1.2 配置文件:

    (1)log4j:

    <?xml version="1.0" encoding="UTF-8" ?>
    <!DOCTYPE log4j:configuration SYSTEM "log4j.dtd">
    <log4j:configuration>
    
        <!--无缓存,立即输出-->
        <appender name="FILE" class="org.apache.log4j.FileAppender">
            <param name="File" value="e:/log.out" />
            <param name="append" value="true"/>
            <layout class="org.apache.log4j.PatternLayout">
                <param name="ConversionPattern" value="%d{HH:mm:ss.SSS} %p %c - %m%n" />
            </layout>
        </appender>
    
        <!--有缓存,不立即输出-->
        <appender name="FILE" class="org.apache.log4j.FileAppender">
            <param name="File" value="e:/log.out" />
            <param name="append" value="true"/>
            <param name="immediateFlush" value="false"/>
            <param name="bufferedIO" value="true"/>
            <param name="bufferSize" value="8192"/>
            <layout class="org.apache.log4j.PatternLayout">
                <param name="ConversionPattern" value="%d{HH:mm:ss.SSS} %p %c - %m%n" />
            </layout>
        </appender>
    
        <!--异步appender-->
        <appender name="AsyncAppender" class="org.apache.log4j.AsyncAppender">
            <appender-ref ref="FILE"/>
        </appender>
    
        <root>
            <priority value="info" />
            <appender-ref ref="FILE" />
            <appender-ref ref="AsyncAppender" />
        </root>
    </log4j:configuration>
    

    (2)logback:

    <configuration >
    
        <!--无缓存,立即输出-->
        <appender name="FILE" class="ch.qos.logback.core.FileAppender">
            <file>e:/log.out</file>
            <append>true</append>
            <encoder>
                <pattern>%d{HH:mm:ss.SSS} %p %c - %m%n</pattern>
            </encoder>
        </appender>
    
        <!--有缓存,不立即输出-->
        <appender name="FILE" class="ch.qos.logback.core.FileAppender">
            <file>e:/log.out</file>
            <append>true</append>
            <immediateFlush>false</immediateFlush>
            <bufferSize>8192</bufferSize>
            <encoder>
                <pattern>%d{HH:mm:ss.SSS} %p %c - %m%n</pattern>
            </encoder>
        </appender>
    
        <!--异步appender-->
        <appender name ="ASYNC" class= "ch.qos.logback.classic.AsyncAppender">  
            <discardingThreshold>0</discardingThreshold>  
            <queueSize>128</queueSize>  
            <appender-ref ref ="FILE"/>  
        </appender>  
        
        <root level="info">
            <appender-ref ref="ASYNC" />
            <appender-ref ref="FILE" />
        </root>
    </configuration>
    

    (3)log4j2:

    <?xml version="1.0" encoding="UTF-8"?>
    <Configuration status="info" monitorInterval="30">
        <Appenders>
    
            <!--无缓存,立即输出-->
           <File name="File" fileName="e:/log.out" append="true">
                <<PatternLayout>
                    <Pattern>%d{HH:mm:ss.SSS} %p %c - %m%n</Pattern>
                </PatternLayout>
            </File>
    
            <!--有缓存,不立即输出-->
            <File name="File" fileName="e:/log.out" append="true"
                  immediateFlush="false" bufferedIO="true" bufferSize="8192">
                <PatternLayout>
                    <Pattern>%d{HH:mm:ss.SSS} %p %c - %m%n</Pattern>
                </PatternLayout>
            </File>
    
           <!--异步appender-->
            <Async name="Async">
                <AppenderRef ref="File"/>
            </Async>
        </Appenders>
        <Loggers>
            <Root level="info" >
                <AppenderRef ref="Async"/>
                <AppenderRef ref="File"/>
            </Root>
            <!--异步logger-->
            <AsyncRoot level="info" >
                <AppenderRef ref="File"/>
            </AsyncRoot>
        </Loggers>
    </Configuration>
    

    1.3 结果比较(毫秒)

    笔者从单线程、多线程2种情况下进行的测试!

    无论是多线程还是单线程,在启用缓存的情况下,系统性能得到了巨大的提升;

    在单线程情况下,相比较来说,启用异步Appender并没有对性能有较大的提升!

    值得一提的是,在log4j2中,多线程情况下,相对于同步logger来说,异步logger并没有进一步提高系统的性能,两者不相上下;

    但是,对于其他情况而言,异步logger还是有较大的提升!

    • 单线程

        (1)单线程,未开启缓存,立即刷出
        
            log4j:29772、29959、30911
            
            logback:25423、24552、26006
            
            log4j2:37927、38240、40164
        
        (2)单线程,开启缓存,不立即刷出
        
            log4j:9858、9677、9665
            
            logback:5561、5604、5611
            
            log4j2:5782、5505、5499
        
        (3)单线程,异步appender,未开启缓存,立即输出
        
            log4j:29683、29929、29385
            
            logback:33102、31779、30516
            
            log4j2:39298、39562、41872
        
        (4)单线程,异步appender,开启缓存,不立即输出
        
            log4j:10110、10068、10177
            
            logback:8753、9112、8922
            
            log4j2:8692、8400、8252
      
    • 多线程

        (1)多线程,未开启缓存,立即刷出
      
            log4j:38541、37791、38366
        
            logback:35644、35463、35442
            
            log4j2:38544、38746、38706
        
        (2)多线程,开启缓存,不立即刷出
      
            log4j:13296、12938、12686
            
            logback:6547、6294、6576
            
            log4j2:5596、5423、5421
        
        (3)多线程,异步appender,未开启缓存,立即输出
      
            log4j:30844、32088、30734
            
            logback:44203、42191、43228
            
            log4j2:46804、46034、46232
        
        (4)多线程,异步appender,开启缓存,不立即输出
      
            log4j:10422、10204、10495
            
            logback:40249、40437、40173
            
            log4j2:7832、8447、8660
      
        (5)多线程,异步logger,未开启缓存,立即输出
      
            log4j2:40555、40245、40325
        
        
        (6)多线程,异步logger,开启缓存,不立即刷出
      
            log4j2:5319、5407、5305

    相关文章

      网友评论

        本文标题:Java日志框架性能比较

        本文链接:https://www.haomeiwen.com/subject/dmxwqxtx.html