Zunächst möchte ich ein Array von Grundelementen und Box-Typen erstellen und sehen, wie viel Speicher verwendet wird.
private static final int NUM = 100_000;
public static void main(String[] args) {
long beforeUse, afterUse, div;
beforeUse = memoryUsed();
int[] primitive = new int[NUM];
afterUse = memoryUsed();
div = afterUse - beforeUse;
out.println(" -- int[] -- ");
out.println(div);
out.println((double)div / primitive.length);
beforeUse = memoryUsed();
Integer[] classes = new Integer[NUM];
afterUse = memoryUsed();
div = afterUse - beforeUse;
out.println(" -- Integer[] unset -- ");
out.println(div);
out.println((double)div / classes.length);
for (int i = 0;i < classes.length;i++) {
classes[i] = i;
}
afterUse = memoryUsed();
div = afterUse - beforeUse;
out.println(" -- Integer[] set -- ");
out.println(div);
out.println((double)div / classes.length);
}
Ausführungsergebnis
-- boolean[] --
100016
1.00016
-- Boolean[] unset --
400016
4.00016
-- Boolean[] set --
400016
4.00016
-- byte[] --
100016
1.00016
-- Byte[] unset --
400016
4.00016
-- Byte[] set --
448528
4.48528
-- short[] --
200016
2.00016
-- Short[] unset --
400016
4.00016
-- Short[] set --
1923440
19.2344
-- char[] --
200016
2.00016
-- Character[] unset --
400016
4.00016
-- Character[] set --
2402512
24.02512
-- int[] --
400016
4.00016
-- Integer[] unset --
400016
4.00016
-- Integer[] set --
2202512
22.02512
-- long[] --
1048576
10.48576
-- Long[] unset --
400016
4.00016
-- Long[] set --
3105872
31.05872
-- float[] --
400016
4.00016
-- Float[] unset --
400016
4.00016
-- Float[] set --
2706352
27.06352
-- double[] --
1048576
10.48576
-- Double[] unset --
400016
4.00016
-- Double[] set --
3651112
36.51112
Schimmel | Primitive | BoxSchimmel(unset) | BoxSchimmel(set) |
---|---|---|---|
boolean / Boolean | 1.00 | 4.00 | 4.00 |
byte / Byte | 1.00 | 4.00 | 4.48 |
short / Short | 2.00 | 4.00 | 19.23 |
char / Character | 2.00 | 4.00 | 24.03 |
int / Integer | 4.00 | 4.00 | 27.06 |
long / Long | 10.49 | 4.00 | 36.51 |
float / Float | 4.00 | 4.00 | 27.06 |
double / Double | 10.49 | 4.00 | 31.06 |
Wenn ich ein Array erstelle, verwende ich immer 16 Bytes. Ich bin nicht sicher, ob die Grundelemente mehr Speicher beanspruchten als lange und doppelt erwartet. Ist es strengstens verboten, es häufig zu verwenden, da es sich um einen Box-Typ (Satz) handelt und nach Zeichen 20 Byte oder mehr verwendet?
Werfen wir einen Blick auf die Speichernutzung der String-Klasse.
// set empty
for (int i = 0;i < NUM;i++) {
ary[i] = "";
}
// set new String
for (int i = 0;i < NUM;i++) {
ary[i] = new String();
}
// set 10digit
for (int i = 0;i < NUM;i++) {
ary[i] = new String("0123456789");
}
-- String[] unset --
400016
4.00016
-- String[] set empty --
400016
4.00016
-- String[] set new String --
3105872
31.05872
-- String[] set 10digit --
3105872
31.05872
New String
für alle Elemente verbraucht ungefähr 31 Bytes. Es ist jedoch seltsam, dass sogar "neuer String (" 0123456789 ")" 31 Bytes beträgt.
Liegt es daran, dass das interne Element private final byte [] value;
immer dieselbe Referenz ist?
Also habe ich es so korrigiert, dass alle Elemente einzigartig sind.
for (int i = 0;i < NUM;i++) {
ary[i] = String.format("%010d", i);
}
System.gc();
-- String[] set 10digit --
4998968
49.98968
Es wurden 49 Bytes pro Element.
HashMap
Fügen Sie 100.000 Elemente in HashMap ein.
Map<String, String> map = new HashMap<>();
for (int i = 0;i < NUM;i++) {
map.put(String.valueOf(i), "A" + i);
}
13632176
136.32176
Es wurden 136 Bytes pro Element. Es scheint, dass Sie es lesen müssen, weil Sie die Gründe nur verstehen können, wenn Sie sich die Implementierung ansehen.
Recommended Posts