我试图理解java中的编译与运行时计算。我有以下内容 枚举
public enum SightSensor{
NORTH (new MapLocation[]{new MapLocation(0,1),
new MapLocation(0,2),
new MapLocation(0,3)}),
SOUTH (new MapLocation[]{new MapLocation(0,-1),
new MapLocation(0,-2),
new MapLocation(0,-3)});
private final MapLocation[] locs;
SightSensor(MapLocation[] locs){
this.locs = locs;
}
public static MapLocation[] getLocs(Direction dir){
if (dir == Direction.NORTH)
return NORTH.locs;
if (dir == Direction.SOUTH)
return SOUTH.locs;
}
};
换句话说,我想定义一个 Direction 和数组之间的常量映射 map 位置。 (也许这是错误的方法?我是 Java 新手。)现在,如果我 写
MapLocation[] locs = SightSensor.getLocs(Direction.SOUTH_WEST);
在代码的循环内,我发现第一次执行代码时存在成本开销 被调用,对我来说意味着它在运行时以某种方式被计算/实例化。如果相反 我直接编码
MapLocation[] locs = new MapLocation[]{new MapLocation(0,1),
new MapLocation(0,2),
new MapLocation(0,3)};
没有成本开销。我不明白其中的区别。编译器是否做了一些事情 奇怪的即时计算?
最佳答案
您看到的成本似乎是类加载成本:代码第一次访问类时,类加载器将其二进制文件(.class 文件)加载到内存中。这是一次性成本,对于大多数实际用途来说可以忽略不计。
此外:
Now, if I write ... inside a loop in the code, I find that there is a cost overhead the first time the code is called,
你是如何衡量这个成本的?测量单个操作的时间成本几乎是不可能的。您可以测量执行 xM 次循环所需的时间,然后除以得到摊余成本。然而,测量单个操作很困难:您可能会遇到垃圾收集周期、与线程相关的上下文切换等。此外,JIT(即时)编译器不会在第一次执行语句时启动,因此测量单个操作通常会给您带来比 N 次操作的摊余成本高得多的成本。
FWIW,我会编写 getLocs()
如下:
public static MapLocation[] getLocs(Direction dir) {
return valueOf(dir.name()).locs;
}
或者,您可以使用 EnumMap 类型的变量替换 SightSensor 枚举:
EnumMap<Direction, MapLocation[]> map = new EnumMap(Direction.class);
map.put(Direction.NORTH, new MapLocation[] { new MapLocation(0, 1),
new MapLocation(0, 2),
new MapLocation(0, 3) });
map.put(Direction.NORTH, new MapLocation[] { new MapLocation(0, -1),
new MapLocation(0, -2),
new MapLocation(0, -3) });
然后,getLocs()
调用就变成了 map.get(dir)
关于java 编译与运行时计算,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8705539/