我有以下几点:
double timeInMinutes = (double) timeInMilliseconds / (1000 * 60);
操作(1000*60)
是在编译时还是在运行时完成的?换句话说,在运行时,上述代码段和以下代码段之间是否存在性能差异:
double timeInMinutes = (double) timeInMilliseconds / 60000;
编辑:我的问题不同于Java编译器是否会预先计算文字的总和?,因为我在算术运算中混合使用变量和文字。虽然差别很小,但正如@TagirValeev在评论中指出的(对文本的算术运算是在编译时还是在运行时计算的?),有些情况下,某些文字没有预先编译,即使它们可能是。
只需创建类测试
public class Test {
public static void main(String [] args) {
long timeInMilliseconds = System.currentTimeMillis();
double timeInMinutes = (double) timeInMilliseconds / (1000 * 60);
System.out.println(timeInMinutes);
}
}
并使用命令javap-v Test对其进行反编译
您可以看到反编译类的输出:
public static void main(java.lang.String[]);
flags: ACC_PUBLIC, ACC_STATIC
Code:
stack=4, locals=5, args_size=1
0: invokestatic #2 // Method java/lang/System.currentTimeMillis:()J
3: lstore_1
4: lload_1
5: l2d
6: ldc2_w #3 // double 60000.0d
9: ddiv
10: dstore_3
11: getstatic #5 // Field java/lang/System.out:Ljava/io/PrintStream;
14: dload_3
15: invokevirtual #6 // Method java/io/PrintStream.println:(D)V
18: return
LineNumberTable:
line 3: 0
line 4: 4
line 5: 11
line 6: 18
看看第6行:ldc2#U w#3//double 60000.0d
在编译时。这是最基本的编译器优化之一,称为常数折叠。
根据JLS§15.2-表达形式
有些表达式的值可以在编译时确定。这些是常量表达式(§15.28)。
像*、/、和%
这样的乘法运算符属于常量表达式,因此它将在编译时确定。
@SergeyMorozov比我更快地编写和获得字节码证明(#2=整数60000
),但这是实际证明,以上是理论/官方声明:
尝试在您的终端生成字节代码,以及使用1000*60
和60000
,您将看到相同的字节代码指令,因此将有相同的运行时性能。
Java类:
public class Test {
public static void main(String[] args) {
int compileTest = 1000 * 60;
}
}
字节码:
Classfile /E:/Test.class
Last modified Oct 9, 2015; size 265 bytes
MD5 checksum fd115be769ec6ef7995e4c84f7597d67
Compiled from "Test.java"
public class Test
SourceFile: "Test.java"
minor version: 0
major version: 51
flags: ACC_PUBLIC, ACC_SUPER
Constant pool:
#1 = Methodref #4.#13 // java/lang/Object."<init>":()V
#2 = Integer 60000
#3 = Class #14 // Test
#4 = Class #15 // java/lang/Object
#5 = Utf8 <init>
#6 = Utf8 ()V
#7 = Utf8 Code
#8 = Utf8 LineNumberTable
#9 = Utf8 main
#10 = Utf8 ([Ljava/lang/String;)V
#11 = Utf8 SourceFile
#12 = Utf8 Test.java
#13 = NameAndType #5:#6 // "<init>":()V
#14 = Utf8 Test
#15 = Utf8 java/lang/Object
{
public Test();
flags: ACC_PUBLIC
Code:
stack=1, locals=1, args_size=1
0: aload_0
1: invokespecial #1 // Method java/lang/Object."<init>":()V
4: return
LineNumberTable:
line 1: 0
public static void main(java.lang.String[]);
flags: ACC_PUBLIC, ACC_STATIC
Code:
stack=1, locals=2, args_size=1
0: ldc #2 // int 60000
2: istore_1
3: return
LineNumberTable:
line 3: 0
line 4: 3
}
下面是代码 在类中,我使用参数10/3调用方法(如代码中所示)。由于callMtd在baseClass中重载,默认情况下应该调用哪个版本?因为它是重载的,方法绑定应该在编译时发生,但是10/3的计算能在编译时发生吗?
问题内容: 是否可以查询两个字段之间相减的结果? 例如,有两个字段:“开始”,“结束”。我想要带的文件。 可以直接完成此操作吗,还是唯一的方法是在加载具有这种差异的文档时创建一个新字段? 问题答案: 查询中的脚本过滤器可能是解决方法。 http://www.elasticsearch.org/guide/zh- CN/elasticsearch/reference/current/query-ds
我正在学习如何通过OCA考试,并坚持这个java字符串池的概念。 考虑以下几点: 和在字符串中是相同的,在对象中也是相同的,因为它是相同的字符串文本,所以JVM在编译时将字符串池和。 现在,是在运行时计算的,因此应该返回一个新字符串。因此,应该为false,但事实并非如此。为什么? 我的一个理论是方法首先检查是否有空白需要删除,如果没有,则简单返回本身。这可以解释为什么s1==s3,但我不确定。
这两个类路径能完全不同吗?
我试图计算变量,但我的答案是错误的(警告:除以零),我假设它是因为默认情况下,我的变量实际上是零。 我怎么能重写这个来检查它是否为零,只有运行计算,如果它不是零? 除此之外,当我的变量不是“0”时,代码可以完美地工作 在编辑脚本之前,默认情况下所有变量都是“0”。
主要内容:numpy.reciprocal(),numpy.power(),numpy.mod(),复数数组处理函数NumPy 数组的“加减乘除”算术运算,分别对应 add()、subtract()、multiple() 以及 divide() 函数。 注意:做算术运算时,输入数组必须具有相同的形状,或者符合数组的广播规则,才可以执行运算。 下面看一组示例: 输出结果: 下面介绍了 NumPy 中其他重要的算术运算函数。 numpy.reciprocal() 该函数对数组中的每个元素取倒数,并