I am trying to run a simple JUnit test that includes the following code:
@Test
public void testVeryLongString() {
String s = "0123456789";
String repeated = new String(new char[214748364]).replace("\0", s);
assertEquals(2147483640, repeated .length());
}
It fails on the above lines with "Requested array size exceeds VM limit".
I tried increasing the Run Configuration of this test to -Xmx18292m (on a 64GB Windows workstation) but I am still getting the dreaded "Requested array size exceeds VM limit".
What am I missing?
Is there a way to let the test proceed without failing on this VM limit?
Requested array size exceeds VM limit means that an array greater than Integer.MAX_VALUE
is attempted to be allocated. Since Java 9 String
and StringBuilder
(which is used for String.replace(...)
) internally use each a byte array twice the size of the string length instead of a char
array of the same length.
With Java 8 and enough memory (much more than -Xmx18292m
as additional arrays are required for doing String.replace(...)
) to avoid an OutOfMemoryError
, it should work.
For better performance and less memory requirements, use the following code:
@Test
public void testVeryLongString() {
String s = "0123456789";
char[] chars = new char[214_748_364 * s.length()]; // Java 9+: 107_374_182
for (int i = 0; i < chars.length; i += s.length()) {
for (int j = 0; j < s.length(); j++) {
chars[i+j] = s.charAt(j);
}
}
String repeated = new String(chars);
assertEquals(2_147_483_640, repeated.length()); // Java 9+: 1_073_741_820
}