gpt4 book ai didi

java - ArrayLists 比数组慢 2 倍

转载 作者:塔克拉玛干 更新时间:2023-11-03 05:02:54 24 4
gpt4 key购买 nike

我正在测试一种分子动力学算法,其中包括一个由 9 个 double 组 组成的粒子类,用于存储粒子分量(3D 环境中的速度、力和位置)。

我使用 5 个输入大小测试算法:

Size (MB) Time (s)
0.06 0.36 (fits in cache L2)
0.14 1.79 (fits in cache L2)
0.60 36.86 (fits in cache L3)
1.35 182.24 (fits in cache L3)
17.38 566.55 (it only fits in RAM)

然后我将 Particles 布局从 array 更改为 ArrayList。为了有一个连续的内存块,我创建了 arrayList,其大小将占用:

ArrayList <Double> px = new ArrayList <Double>(Input_Size);

我在与上述相同的睾丸条件下运行该版本,结果是:

Size (MB) Time (s)
0.06 0.608
0.14 2.78
0.60 57.15
1.35 299.24
17.38 1436,42

测试环境为:

AMD Opteron 处理器 6174、800 MHz、12 MB 三级缓存,24 核;

我的速度降低了大约 2 倍。这是正常的吗?不应期望两个版本中的时间几乎相同,因为 ArrayList 像数组一样在内存中连续分配?

编辑:

Running with the option **-XX:+PrintCompilation**

WITH ARRAY:

1 java.util.jar.Manifest$FastInputStream::readLine (167 bytes)
2 sun.nio.cs.UTF_8$Decoder::decodeArrayLoop (553 bytes)
3 java.lang.String::hashCode (60 bytes)
4 java.lang.String::charAt (33 bytes)
5 sun.security.util.ManifestDigester::findSection (180 bytes)
6 java.lang.Object::<init> (1 bytes)
7 moldyn.random::update (104 bytes)
8 moldyn.random::seed (80 bytes)
--- n java.lang.StrictMath::log (static)
9 java.lang.Math::log (5 bytes)
10 moldyn.md::scalingVelocity (82 bytes)
11 moldyn.Particles::distance (192 bytes)
1% moldyn.Particles::force @ 42 (211 bytes)
12 moldyn.Particles::force (211 bytes)
13 moldyn.Particles::domove (163 bytes)
14 moldyn.Particles::domove_out (160 bytes)
2% moldyn.Particles::cicle_domove @ 5 (23 bytes)
15 moldyn.Particles::update_force (49 bytes)
3% moldyn.Particles::cicle_forces @ 6 (27 bytes)
16 moldyn.Particles::mkekin (141 bytes)
4% moldyn.Particles::cicle_mkekin @ 9 (33 bytes)
17 moldyn.Particles::velavg (70 bytes)
5% moldyn.Particles::cicle_velavg @ 9 (37 bytes)
18 moldyn.Particles::cicle_domove (23 bytes)
19 moldyn.Particles::cicle_forces (27 bytes)
20 moldyn.Particles::cicle_mkekin (33 bytes)
21 moldyn.Particles::cicle_velavg (37 bytes)
36.763

WITH ArrayList <Double>....
----

1 java.util.jar.Manifest$FastInputStream::readLine (167 bytes)
2 sun.nio.cs.UTF_8$Decoder::decodeArrayLoop (553 bytes)
3 java.lang.String::hashCode (60 bytes)
4 java.lang.String::charAt (33 bytes)
5 sun.security.util.ManifestDigester::findSection (180 bytes)
6 java.lang.Object::<init> (1 bytes)
--- n java.lang.System::arraycopy (static)
7 java.lang.Number::<init> (5 bytes)
8 java.util.ArrayList::ensureCapacity (58 bytes)
9 java.lang.Double::valueOf (9 bytes)
10 java.lang.Double::<init> (10 bytes)
11 java.util.ArrayList::add (100 bytes)
12 java.util.ArrayList::RangeCheck (48 bytes)
13 java.util.ArrayList::set (21 bytes)
14 moldyn.random::update (104 bytes)
15 moldyn.random::seed (80 bytes)
--- n java.lang.StrictMath::log (static)
16 java.lang.Math::log (5 bytes)
17 java.util.ArrayList::get (12 bytes)
18 java.lang.Double::doubleValue (5 bytes)
19 moldyn.md::scalingVelocity (120 bytes)
20 moldyn.Particles::distance (240 bytes)
1% moldyn.Particles::force @ 42 (211 bytes)
21 moldyn.Particles::force (211 bytes)
22 moldyn.Particles::domove (337 bytes)
23 moldyn.Particles::domove_out (292 bytes)
2% moldyn.Particles::cicle_domove @ 5 (23 bytes)
24 moldyn.Particles::update_force (91 bytes)
3% moldyn.Particles::cicle_forces @ 6 (27 bytes)
25 moldyn.Particles::mkekin (297 bytes)
4% moldyn.Particles::cicle_mkekin @ 9 (33 bytes)
26 moldyn.Particles::velavg (118 bytes)
5% moldyn.Particles::cicle_velavg @ 9 (37 bytes)
27 moldyn.Particles::cicle_domove (23 bytes)
28 moldyn.Particles::cicle_forces (27 bytes)
29 moldyn.Particles::cicle_mkekin (33 bytes)
30 moldyn.Particles::cicle_velavg (37 bytes)
55.98

最佳答案

我有一些想法,但没有确定的答案:

  1. A java.lang.Doubledouble 不同原始。可能是自动装箱开销和额外的机器伴随着 Double对象有所作为。我会比较字节码,看看这是不是真的。
  2. 这听起来像是 double [] 的选择或 List<Double>在您的 Particle 中对客户隐藏类(class)。如果是这种情况,请使用数组,因为它是一个内部实现细节。
  3. 我会小心不要用基准测试来欺骗自己。
  4. 我想知道你的 Particle类是否可变。这可能会有所作为。位置、速度和力是否不断变化并在您的对象中得到更新?

关于java - ArrayLists 比数组慢 2 倍,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13553950/

24 4 0