Java 两次强制转换或创建新实例是否更有效
考虑这两段代码(您可以假设Java 两次强制转换或创建新实例是否更有效,java,casting,Java,Casting,考虑这两段代码(您可以假设execeptionObj属于Object类型,但我们知道它是Throwable的一个实例): (一) (二) 在我正在进行的一个项目的代码评审中,一位评审员说第一种方法不如第二种方法有效,因为它涉及两个类型转换。我只是想知道你是怎么想的。创建一个新实例似乎也会涉及一些开销。考虑到一个异常的成本以及仅仅打印出内容的成本,我认为这场辩论有点似是而非 考虑到一个例外和仅仅打印内容的成本,我认为这场辩论有点似是而非 这两段代码做不同的事情。在第二种情况下,您不再传递excep
execeptionObj
属于Object
类型,但我们知道它是Throwable
的一个实例):
(一)
(二)
在我正在进行的一个项目的代码评审中,一位评审员说第一种方法不如第二种方法有效,因为它涉及两个类型转换。我只是想知道你是怎么想的。创建一个新实例似乎也会涉及一些开销。考虑到一个异常的成本以及仅仅打印出内容的成本,我认为这场辩论有点似是而非 考虑到一个例外和仅仅打印内容的成本,我认为这场辩论有点似是而非 这两段代码做不同的事情。在第二种情况下,您不再传递exceptionObj,而是“由exceptionObj引起的未指定的丢弃”。我认为那不是你想要的 你是说第二行的第一行是:
Throwable t = (Throwable) exceptionObj;
我想它的效率会稍微高一些,但不会让它决定问题。哪个更具可读性是关键,我认为(修改后的)第二个更具可读性
你真的要把箱子扔掉吗?当然,记录器已经可以丢弃了吗?这两段代码做了不同的事情。在第二种情况下,您不再传递exceptionObj,而是“由exceptionObj引起的未指定的丢弃”。我认为那不是你想要的 你是说第二行的第一行是:
Throwable t = (Throwable) exceptionObj;
我想它的效率会稍微高一些,但不会让它决定问题。哪个更具可读性是关键,我认为(修改后的)第二个更具可读性
你真的要把箱子扔掉吗?那伐木工人肯定已经被抛弃了
exceptionObj
是字符串或可丢弃的时编译。如果是字符串
,则第一个示例根本无法编译,如果是可丢弃的
,则在第一个示例中不需要强制转换
Throwable
以避免强制转换是一件可怕的事情,因为它改变了代码的实际功能exceptionObj
是字符串或可丢弃的时编译。如果是字符串
,则第一个示例根本无法编译,如果是可丢弃的
,则在第一个示例中不需要强制转换
Throwable
以避免强制转换是一件可怕的事情,因为它改变了代码的实际功能为什么不施放一次并使用两次呢
Throwable t = (Throwable) exceptionObj;
如果不分析并使用重载,就很难说出实际答案。为什么不施放一次并使用两次呢
Throwable t = (Throwable) exceptionObj;
logger.log(Level.ERROR, (Throwable) exceptionObj,
((Throwable) exceptionObj).getMessage());
如果不分析和使用重载,就很难说出实际答案
logger.log(Level.ERROR, (Throwable) exceptionObj,
((Throwable) exceptionObj).getMessage());
从理论上讲,这将导致两种类型铸件的成本。实际上,JIT编译器可能会将其优化为只执行一次类型转换的本机代码
Throwable t = new Throwable((Throwable)exceptionObj);
logger.log(Level.ERROR, t, t.getMessage());
这里我们用一个类型转换和一个对象创建替换两个类型转换。但是,创建的对象是可丢弃的,如果您查看Throwable的构造函数,您会注意到它调用fillInStackTrace()
。此方法创建一组其他对象来记录有关堆栈的信息,这可能比执行(成功的)类型转换要昂贵得多。此外,这个类型转换很有可能已经被优化掉了
显然,彻底的调查需要分析两个版本的代码,并检查JIT编译器生成的本机代码
(正如其他人所指出的,这两段代码的效果是不同的。第一段记录原始异常,第二段记录新的Throwable,原始异常作为嵌套异常。)
从理论上讲,这将导致两种类型铸件的成本。实际上,JIT编译器可能会将其优化为只执行一次类型转换的本机代码
Throwable t = new Throwable((Throwable)exceptionObj);
logger.log(Level.ERROR, t, t.getMessage());
这里我们用一个类型转换和一个对象创建替换两个类型转换。但是,创建的对象是一个Throwable,如果查看Throwable的构造函数,您会注意到它调用fillInStackTrace()
。此方法创建一组其他对象来记录有关堆栈的信息,这可能比执行(成功的)类型转换要昂贵得多。此外,这个类型转换很有可能已经被优化掉了
显然,彻底的调查需要分析两个版本的代码,并检查JIT编译器生成的本机代码
(正如其他人所指出的,这两段代码的效果是不同的。第一段记录原始异常,第二段记录新的Throwable,原始异常作为嵌套异常。)不,我是说我写的。下面是评论员的原话:“你最好创建一个实例,使用2个casting是没有效率的”。强制转换是必要的,因为我正在为日志调用使用以下签名:Log.Log(Level,Throwable,String)@dcp:casting两次总是比创建对象快得多。此外,“创建实例”代码也无法编译。@dcp By usi