Java LoggerFactory.getLogger(ClassName.class) vs LoggerFactory.getLogger(this.getClass().getName())
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/33779127/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
LoggerFactory.getLogger(ClassName.class) vs LoggerFactory.getLogger(this.getClass().getName())
提问by Aurasphere
I'm trying to improve my optimization skills in Java. In order to achieve that, I've got an old program I made and I'm trying my best to make it better. In this program I'm using SL4J for logging. To get the logger I did:
我正在努力提高我的 Java 优化技能。为了实现这一目标,我制作了一个旧程序,并且正在尽最大努力让它变得更好。在这个程序中,我使用 SL4J 进行日志记录。为了得到记录器,我做了:
private static final Logger logger = LoggerFactory.getLogger(this.getClass().getName());
At the time I wrote the code, I thought this was the best option, because I remove a reference to the class name(which may be refactored). But now I'm not so sure anymore...
在我写代码的时候,我认为这是最好的选择,因为我删除了对类名的引用(可能会被重构)。但现在我不太确定了......
private static final Logger logger = LoggerFactory.getLogger(ClassName.class);
On the other side, keeps the reference to the class name, but it removes one method call. This may not be a big improvement in performance for one class, but when you have lots of class, this may be something.
另一方面,保留对类名的引用,但它删除了一个方法调用。对于一个班级来说,这可能不是一个很大的性能改进,但是当你有很多班级时,这可能是一些事情。
So my question is:
所以我的问题是:
Which approach is better? Using the class name or getting it through reflection?
哪种方法更好?使用类名还是通过反射获取?
Please, motivate your answer with pro and cons. Thank you.
请用利弊来激励你的答案。谢谢你。
采纳答案by Mark Bramnik
I'll share my opinion here. I would say that this is the case that you shouldn't be bothered from the performance point of view. Probably in the code there are parts that can be optimized much more than this thing :)
我会在这里分享我的看法。我想说的是,从性能的角度来看,您不应该受到打扰。可能在代码中有比这件事可以优化的部分:)
Now, regarding your question. Take a look on LoggerFactory'scode
现在,关于你的问题。看一下LoggerFactory 的代码
Note that getLogger(Class<?> name)
just calls the overloaded method:
注意getLogger(Class<?> name)
只是调用了重载的方法:
Logger logger = getLogger(clazz.getName());
And makes some additional calculations. So the method with String is obviously slightly faster.
并进行一些额外的计算。所以带String的方法显然要快一些。
In general the pattern is to maintain the Logger reference as a static field in the class, something like this:
一般来说,模式是将 Logger 引用作为类中的静态字段来维护,如下所示:
public class SomeClass {
private static final Logger LOG = LoggerFactory.getLogger(SomeClass.class);
}
In this case you can't really use this.getClass()
because this
doesn't actually exists (you're running in a static context).
在这种情况下,您不能真正使用,this.getClass()
因为this
实际上并不存在(您在静态上下文中运行)。
From my experience its better to use the ClassName.getClass()
as a parameter unless you really want to use the same logger from different classes. In such a case you better use some logical constant that denotes the logger.
根据我的经验,最好将ClassName.getClass()
用作参数,除非您真的想使用来自不同类的相同记录器。在这种情况下,您最好使用一些表示记录器的逻辑常量。
For example, let's say you're trying to use 3 different classes to access the database. So you create logger 'DB', assign a file appender that will write to database.log and you want to reuse the same logger among these 3 different classes.
例如,假设您尝试使用 3 个不同的类来访问数据库。因此,您创建记录器“DB”,分配将写入 database.log 的文件附加程序,并且您希望在这 3 个不同的类中重用相同的记录器。
So you should use the following code:
所以你应该使用以下代码:
public class SomeClass {
private static final Logger LOG = LoggerFactory.getLogger("DB");
}
Hope this helps
希望这可以帮助
回答by francesco foresti
What I usually do is
我通常做的是
private static final Logger logger = LoggerFactory.getLogger(ClassName.class);
However, the idiom
然而,成语
protected final Logger log = LoggerFactory.getLogger(getClass());
is equally common. In this questionyou can find more info about these conventions.
同样常见。在这个问题中,您可以找到有关这些约定的更多信息。
回答by D. Rakov
I prefer
我更喜欢
Logger logger = LoggerFactory.getLogger(ClassName.class);
Because
因为
this.getClass()
Can be override by one of class children and you will see child class name in log. Sometimes it can be confusing because log actually is performed in parent class
可以由班级孩子之一覆盖,您将在日志中看到子班级名称。有时可能会令人困惑,因为日志实际上是在父类中执行的
回答by Somendra
I use this
我用这个
private static final Logger log = LoggerFactory.getLogger(ClassName.class);
回答by baronKarza
If you don't want to write the class name every time you declare a logger, you can use the following utility method:
如果不想每次声明记录器都写类名,可以使用下面的实用方法:
public static org.slf4j.Logger getLogger() {
final Throwable t = new Throwable();
t.fillInStackTrace();
return LoggerFactory.getLogger(t.getStackTrace()[1].getClassName());
}
The method can be used tis way:
该方法可以使用tis方式:
private static final Logger LOG = TheClassContainingTheMethod.getLogger();
With such an approach, the logger declaration is always the same for all the classes.
使用这种方法,所有类的记录器声明总是相同的。
回答by Nikhil
Use this
用这个
private final Logger logger = LoggerFactory.getLogger(this.getClass());
}
// logic
try
{
// todo
}
catch (NullPointerException e) {
logger.error("Error:-" + e.getMessage());
return ResponseUtil.errorResponse(e.getMessage());
}
catch (Exception e) {
logger.error("Error:-" + e.getMessage());
return ResponseUtil.errorResponse(e.getMessage());
}
回答by Mark McLaren
Late entry!
迟到!
As I am likely to be searching for this in the future.
因为我将来可能会寻找这个。
There is a way to create copy/paste friendly Logger instances (granted this is almost never a good reason to do something!) by using Java 7's MethodHandles class.
有一种方法可以通过使用 Java 7 的 MethodHandles 类来创建对复制/粘贴友好的 Logger 实例(当然这几乎从来都不是做某事的好理由!)。
private static final Logger LOGGER = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass());