Repository: commons-lang Updated Branches: refs/heads/master 0136218fa -> 795fe5d86
Added new vararg methods to insert values into an array at an index. This implements LANG-660. This commit also deprecates the add() methods that inserted a single value into an array at an index. Project: http://git-wip-us.apache.org/repos/asf/commons-lang/repo Commit: http://git-wip-us.apache.org/repos/asf/commons-lang/commit/795fe5d8 Tree: http://git-wip-us.apache.org/repos/asf/commons-lang/tree/795fe5d8 Diff: http://git-wip-us.apache.org/repos/asf/commons-lang/diff/795fe5d8 Branch: refs/heads/master Commit: 795fe5d869594bde53f8490d75eedef6185b6c37 Parents: 0136218 Author: duncan <dun...@wortharead.com> Authored: Mon Dec 12 14:00:19 2016 +0000 Committer: duncan <dun...@wortharead.com> Committed: Mon Dec 12 14:00:19 2016 +0000 ---------------------------------------------------------------------- src/changes/changes.xml | 1 + .../org/apache/commons/lang3/ArrayUtils.java | 431 +++++++++++++++++++ .../commons/lang3/ArrayUtilsInsertTest.java | 349 +++++++++++++++ 3 files changed, 781 insertions(+) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/commons-lang/blob/795fe5d8/src/changes/changes.xml ---------------------------------------------------------------------- diff --git a/src/changes/changes.xml b/src/changes/changes.xml index 994ad1b..c4603fa 100644 --- a/src/changes/changes.xml +++ b/src/changes/changes.xml @@ -46,6 +46,7 @@ The <action> type attribute can be add,update,fix,remove. <body> <release version="3.6" date="2016-MM-DD" description="TBD"> + <action issue="LANG-660" type="add" dev="djones">Add methods to insert arrays into arrays at an index</action> <action issue="LANG-1292" type="fix" dev="djones">WordUtils.wrap throws StringIndexOutOfBoundsException</action> <action issue="LANG-1287" type="fix" dev="pschumacher" due-to="Ivan Morozov">RandomStringUtils#random can enter infinite loop if end parameter is to small</action> <action issue="LANG-1285" type="fix" dev="pschumacher" due-to="Francesco Chicchiriccò">NullPointerException in FastDateParser$TimeZoneStrategy</action> http://git-wip-us.apache.org/repos/asf/commons-lang/blob/795fe5d8/src/main/java/org/apache/commons/lang3/ArrayUtils.java ---------------------------------------------------------------------- diff --git a/src/main/java/org/apache/commons/lang3/ArrayUtils.java b/src/main/java/org/apache/commons/lang3/ArrayUtils.java index ebb47a8..1e1217b 100644 --- a/src/main/java/org/apache/commons/lang3/ArrayUtils.java +++ b/src/main/java/org/apache/commons/lang3/ArrayUtils.java @@ -5629,7 +5629,11 @@ public class ArrayUtils { * @return A new array containing the existing elements and the new element * @throws IndexOutOfBoundsException if the index is out of range (index < 0 || index > array.length). * @throws IllegalArgumentException if both array and element are null + * @deprecated this method has been superseded by {@link #insert(int, Object[], Object...) insert(int, T[], T...)} and + * may be removed in a future release. Please note the handling of {@code null} input arrays differs + * in the new method: inserting {@code X} into a {@code null} array results in {@code null} not {@code X}. */ + @Deprecated public static <T> T[] add(final T[] array, final int index, final T element) { Class<?> clss = null; if (array != null) { @@ -5669,7 +5673,11 @@ public class ArrayUtils { * @param element the object to add * @return A new array containing the existing elements and the new element * @throws IndexOutOfBoundsException if the index is out of range (index < 0 || index > array.length). + * @deprecated this method has been superseded by {@link #insert(int, boolean[], boolean...)} and + * may be removed in a future release. Please note the handling of {@code null} input arrays differs + * in the new method: inserting {@code X} into a {@code null} array results in {@code null} not {@code X}. */ + @Deprecated public static boolean[] add(final boolean[] array, final int index, final boolean element) { return (boolean[]) add(array, index, Boolean.valueOf(element), Boolean.TYPE); } @@ -5701,7 +5709,11 @@ public class ArrayUtils { * @return A new array containing the existing elements and the new element * @throws IndexOutOfBoundsException if the index is out of range * (index < 0 || index > array.length). + * @deprecated this method has been superseded by {@link #insert(int, char[], char...)} and + * may be removed in a future release. Please note the handling of {@code null} input arrays differs + * in the new method: inserting {@code X} into a {@code null} array results in {@code null} not {@code X}. */ + @Deprecated public static char[] add(final char[] array, final int index, final char element) { return (char[]) add(array, index, Character.valueOf(element), Character.TYPE); } @@ -5732,7 +5744,11 @@ public class ArrayUtils { * @return A new array containing the existing elements and the new element * @throws IndexOutOfBoundsException if the index is out of range * (index < 0 || index > array.length). + * @deprecated this method has been superseded by {@link #insert(int, byte[], byte...)} and + * may be removed in a future release. Please note the handling of {@code null} input arrays differs + * in the new method: inserting {@code X} into a {@code null} array results in {@code null} not {@code X}. */ + @Deprecated public static byte[] add(final byte[] array, final int index, final byte element) { return (byte[]) add(array, index, Byte.valueOf(element), Byte.TYPE); } @@ -5763,7 +5779,11 @@ public class ArrayUtils { * @return A new array containing the existing elements and the new element * @throws IndexOutOfBoundsException if the index is out of range * (index < 0 || index > array.length). + * @deprecated this method has been superseded by {@link #insert(int, short[], short...)} and + * may be removed in a future release. Please note the handling of {@code null} input arrays differs + * in the new method: inserting {@code X} into a {@code null} array results in {@code null} not {@code X}. */ + @Deprecated public static short[] add(final short[] array, final int index, final short element) { return (short[]) add(array, index, Short.valueOf(element), Short.TYPE); } @@ -5794,7 +5814,11 @@ public class ArrayUtils { * @return A new array containing the existing elements and the new element * @throws IndexOutOfBoundsException if the index is out of range * (index < 0 || index > array.length). + * @deprecated this method has been superseded by {@link #insert(int, int[], int...)} and + * may be removed in a future release. Please note the handling of {@code null} input arrays differs + * in the new method: inserting {@code X} into a {@code null} array results in {@code null} not {@code X}. */ + @Deprecated public static int[] add(final int[] array, final int index, final int element) { return (int[]) add(array, index, Integer.valueOf(element), Integer.TYPE); } @@ -5825,7 +5849,11 @@ public class ArrayUtils { * @return A new array containing the existing elements and the new element * @throws IndexOutOfBoundsException if the index is out of range * (index < 0 || index > array.length). + * @deprecated this method has been superseded by {@link #insert(int, long[], long...)} and + * may be removed in a future release. Please note the handling of {@code null} input arrays differs + * in the new method: inserting {@code X} into a {@code null} array results in {@code null} not {@code X}. */ + @Deprecated public static long[] add(final long[] array, final int index, final long element) { return (long[]) add(array, index, Long.valueOf(element), Long.TYPE); } @@ -5856,7 +5884,11 @@ public class ArrayUtils { * @return A new array containing the existing elements and the new element * @throws IndexOutOfBoundsException if the index is out of range * (index < 0 || index > array.length). + * @deprecated this method has been superseded by {@link #insert(int, float[], float...)} and + * may be removed in a future release. Please note the handling of {@code null} input arrays differs + * in the new method: inserting {@code X} into a {@code null} array results in {@code null} not {@code X}. */ + @Deprecated public static float[] add(final float[] array, final int index, final float element) { return (float[]) add(array, index, Float.valueOf(element), Float.TYPE); } @@ -5887,7 +5919,11 @@ public class ArrayUtils { * @return A new array containing the existing elements and the new element * @throws IndexOutOfBoundsException if the index is out of range * (index < 0 || index > array.length). + * @deprecated this method has been superseded by {@link #insert(int, double[], double...)} and + * may be removed in a future release. Please note the handling of {@code null} input arrays differs + * in the new method: inserting {@code X} into a {@code null} array results in {@code null} not {@code X}. */ + @Deprecated public static double[] add(final double[] array, final int index, final double element) { return (double[]) add(array, index, Double.valueOf(element), Double.TYPE); } @@ -8021,4 +8057,399 @@ public class ArrayUtils { return result; } + + /** + * <p>Inserts elements into an array at the given index (starting from zero).</p> + * + * <p>When an array is returned, it is always a new array.</p> + * + * <pre> + * ArrayUtils.insert(index, null, null) = null + * ArrayUtils.insert(index, array, null) = cloned copy of 'array' + * ArrayUtils.insert(index, null, values) = null + * </pre> + * + * @param index the position within {@code array} to insert the new values + * @param array the array to insert the values into, may be {@code null} + * @param values the new values to insert, may be {@code null} + * @return The new array. + * @throws IndexOutOfBoundsException if {@code array} is provided + * and either {@code index < 0} or {@code index > array.length} + * @since 3.6 + */ + public static boolean[] insert(final int index, final boolean[] array, final boolean... values) { + if (array == null) { + return null; + } + if (values == null || values.length == 0) { + return clone(array); + } + if (index < 0 || index > array.length) { + throw new IndexOutOfBoundsException("Index: " + index + ", Length: " + array.length); + } + + boolean[] result = new boolean[array.length + values.length]; + + System.arraycopy(values, 0, result, index, values.length); + if (index > 0) { + System.arraycopy(array, 0, result, 0, index); + } + if (index < array.length) { + System.arraycopy(array, index, result, index + values.length, array.length - index); + } + return result; + } + + + /** + * <p>Inserts elements into an array at the given index (starting from zero).</p> + * + * <p>When an array is returned, it is always a new array.</p> + * + * <pre> + * ArrayUtils.insert(index, null, null) = null + * ArrayUtils.insert(index, array, null) = cloned copy of 'array' + * ArrayUtils.insert(index, null, values) = null + * </pre> + * + * @param index the position within {@code array} to insert the new values + * @param array the array to insert the values into, may be {@code null} + * @param values the new values to insert, may be {@code null} + * @return The new array. + * @throws IndexOutOfBoundsException if {@code array} is provided + * and either {@code index < 0} or {@code index > array.length} + * @since 3.6 + */ + public static byte[] insert(final int index, final byte[] array, final byte... values) { + if (array == null) { + return null; + } + if (values == null || values.length == 0) { + return clone(array); + } + if (index < 0 || index > array.length) { + throw new IndexOutOfBoundsException("Index: " + index + ", Length: " + array.length); + } + + byte[] result = new byte[array.length + values.length]; + + System.arraycopy(values, 0, result, index, values.length); + if (index > 0) { + System.arraycopy(array, 0, result, 0, index); + } + if (index < array.length) { + System.arraycopy(array, index, result, index + values.length, array.length - index); + } + return result; + } + + + /** + * <p>Inserts elements into an array at the given index (starting from zero).</p> + * + * <p>When an array is returned, it is always a new array.</p> + * + * <pre> + * ArrayUtils.insert(index, null, null) = null + * ArrayUtils.insert(index, array, null) = cloned copy of 'array' + * ArrayUtils.insert(index, null, values) = null + * </pre> + * + * @param index the position within {@code array} to insert the new values + * @param array the array to insert the values into, may be {@code null} + * @param values the new values to insert, may be {@code null} + * @return The new array. + * @throws IndexOutOfBoundsException if {@code array} is provided + * and either {@code index < 0} or {@code index > array.length} + * @since 3.6 + */ + public static char[] insert(final int index, final char[] array, final char... values) { + if (array == null) { + return null; + } + if (values == null || values.length == 0) { + return clone(array); + } + if (index < 0 || index > array.length) { + throw new IndexOutOfBoundsException("Index: " + index + ", Length: " + array.length); + } + + char[] result = new char[array.length + values.length]; + + System.arraycopy(values, 0, result, index, values.length); + if (index > 0) { + System.arraycopy(array, 0, result, 0, index); + } + if (index < array.length) { + System.arraycopy(array, index, result, index + values.length, array.length - index); + } + return result; + } + + + /** + * <p>Inserts elements into an array at the given index (starting from zero).</p> + * + * <p>When an array is returned, it is always a new array.</p> + * + * <pre> + * ArrayUtils.insert(index, null, null) = null + * ArrayUtils.insert(index, array, null) = cloned copy of 'array' + * ArrayUtils.insert(index, null, values) = null + * </pre> + * + * @param index the position within {@code array} to insert the new values + * @param array the array to insert the values into, may be {@code null} + * @param values the new values to insert, may be {@code null} + * @return The new array. + * @throws IndexOutOfBoundsException if {@code array} is provided + * and either {@code index < 0} or {@code index > array.length} + * @since 3.6 + */ + public static double[] insert(final int index, final double[] array, final double... values) { + if (array == null) { + return null; + } + if (values == null || values.length == 0) { + return clone(array); + } + if (index < 0 || index > array.length) { + throw new IndexOutOfBoundsException("Index: " + index + ", Length: " + array.length); + } + + double[] result = new double[array.length + values.length]; + + System.arraycopy(values, 0, result, index, values.length); + if (index > 0) { + System.arraycopy(array, 0, result, 0, index); + } + if (index < array.length) { + System.arraycopy(array, index, result, index + values.length, array.length - index); + } + return result; + } + + + /** + * <p>Inserts elements into an array at the given index (starting from zero).</p> + * + * <p>When an array is returned, it is always a new array.</p> + * + * <pre> + * ArrayUtils.insert(index, null, null) = null + * ArrayUtils.insert(index, array, null) = cloned copy of 'array' + * ArrayUtils.insert(index, null, values) = null + * </pre> + * + * @param index the position within {@code array} to insert the new values + * @param array the array to insert the values into, may be {@code null} + * @param values the new values to insert, may be {@code null} + * @return The new array. + * @throws IndexOutOfBoundsException if {@code array} is provided + * and either {@code index < 0} or {@code index > array.length} + * @since 3.6 + */ + public static float[] insert(final int index, final float[] array, final float... values) { + if (array == null) { + return null; + } + if (values == null || values.length == 0) { + return clone(array); + } + if (index < 0 || index > array.length) { + throw new IndexOutOfBoundsException("Index: " + index + ", Length: " + array.length); + } + + float[] result = new float[array.length + values.length]; + + System.arraycopy(values, 0, result, index, values.length); + if (index > 0) { + System.arraycopy(array, 0, result, 0, index); + } + if (index < array.length) { + System.arraycopy(array, index, result, index + values.length, array.length - index); + } + return result; + } + + /** + * <p>Inserts elements into an array at the given index (starting from zero).</p> + * + * <p>When an array is returned, it is always a new array.</p> + * + * <pre> + * ArrayUtils.insert(index, null, null) = null + * ArrayUtils.insert(index, array, null) = cloned copy of 'array' + * ArrayUtils.insert(index, null, values) = null + * </pre> + * + * @param index the position within {@code array} to insert the new values + * @param array the array to insert the values into, may be {@code null} + * @param values the new values to insert, may be {@code null} + * @return The new array. + * @throws IndexOutOfBoundsException if {@code array} is provided + * and either {@code index < 0} or {@code index > array.length} + * @since 3.6 + */ + public static int[] insert(final int index, final int[] array, final int... values) { + if (array == null) { + return null; + } + if (values == null || values.length == 0) { + return clone(array); + } + if (index < 0 || index > array.length) { + throw new IndexOutOfBoundsException("Index: " + index + ", Length: " + array.length); + } + + int[] result = new int[array.length + values.length]; + + System.arraycopy(values, 0, result, index, values.length); + if (index > 0) { + System.arraycopy(array, 0, result, 0, index); + } + if (index < array.length) { + System.arraycopy(array, index, result, index + values.length, array.length - index); + } + return result; + } + + /** + * <p>Inserts elements into an array at the given index (starting from zero).</p> + * + * <p>When an array is returned, it is always a new array.</p> + * + * <pre> + * ArrayUtils.insert(index, null, null) = null + * ArrayUtils.insert(index, array, null) = cloned copy of 'array' + * ArrayUtils.insert(index, null, values) = null + * </pre> + * + * @param index the position within {@code array} to insert the new values + * @param array the array to insert the values into, may be {@code null} + * @param values the new values to insert, may be {@code null} + * @return The new array. + * @throws IndexOutOfBoundsException if {@code array} is provided + * and either {@code index < 0} or {@code index > array.length} + * @since 3.6 + */ + public static long[] insert(final int index, final long[] array, final long... values) { + if (array == null) { + return null; + } + if (values == null || values.length == 0) { + return clone(array); + } + if (index < 0 || index > array.length) { + throw new IndexOutOfBoundsException("Index: " + index + ", Length: " + array.length); + } + + long[] result = new long[array.length + values.length]; + + System.arraycopy(values, 0, result, index, values.length); + if (index > 0) { + System.arraycopy(array, 0, result, 0, index); + } + if (index < array.length) { + System.arraycopy(array, index, result, index + values.length, array.length - index); + } + return result; + } + + + /** + * <p>Inserts elements into an array at the given index (starting from zero).</p> + * + * <p>When an array is returned, it is always a new array.</p> + * + * <pre> + * ArrayUtils.insert(index, null, null) = null + * ArrayUtils.insert(index, array, null) = cloned copy of 'array' + * ArrayUtils.insert(index, null, values) = null + * </pre> + * + * @param index the position within {@code array} to insert the new values + * @param array the array to insert the values into, may be {@code null} + * @param values the new values to insert, may be {@code null} + * @return The new array. + * @throws IndexOutOfBoundsException if {@code array} is provided + * and either {@code index < 0} or {@code index > array.length} + * @since 3.6 + */ + public static short[] insert(final int index, final short[] array, final short... values) { + if (array == null) { + return null; + } + if (values == null || values.length == 0) { + return clone(array); + } + if (index < 0 || index > array.length) { + throw new IndexOutOfBoundsException("Index: " + index + ", Length: " + array.length); + } + + short[] result = new short[array.length + values.length]; + + System.arraycopy(values, 0, result, index, values.length); + if (index > 0) { + System.arraycopy(array, 0, result, 0, index); + } + if (index < array.length) { + System.arraycopy(array, index, result, index + values.length, array.length - index); + } + return result; + } + + + /** + * <p>Inserts elements into an array at the given index (starting from zero).</p> + * + * <p>When an array is returned, it is always a new array.</p> + * + * <pre> + * ArrayUtils.insert(index, null, null) = null + * ArrayUtils.insert(index, array, null) = cloned copy of 'array' + * ArrayUtils.insert(index, null, values) = null + * </pre> + * + * @param index the position within {@code array} to insert the new values + * @param array the array to insert the values into, may be {@code null} + * @param values the new values to insert, may be {@code null} + * @return The new array. + * @throws IndexOutOfBoundsException if {@code array} is provided + * and either {@code index < 0} or {@code index > array.length} + * @since 3.6 + */ + @SafeVarargs + public static <T> T[] insert(final int index, final T[] array, final T... values) { + /* + * Note on use of @SafeVarargs: + * + * By returning null when 'array' is null, we avoid returning the vararg + * array to the caller. We also avoid relying on the type of the vararg + * array, by inspecting the component type of 'array'. + */ + + if (array == null) { + return null; + } + if (values == null || values.length == 0) { + return clone(array); + } + if (index < 0 || index > array.length) { + throw new IndexOutOfBoundsException("Index: " + index + ", Length: " + array.length); + } + + final Class<?> type = array.getClass().getComponentType(); + @SuppressWarnings("unchecked") // OK, because array and values are of type T + T[] result = (T[]) Array.newInstance(type, array.length + values.length); + + System.arraycopy(values, 0, result, index, values.length); + if (index > 0) { + System.arraycopy(array, 0, result, 0, index); + } + if (index < array.length) { + System.arraycopy(array, index, result, index + values.length, array.length - index); + } + return result; + } } http://git-wip-us.apache.org/repos/asf/commons-lang/blob/795fe5d8/src/test/java/org/apache/commons/lang3/ArrayUtilsInsertTest.java ---------------------------------------------------------------------- diff --git a/src/test/java/org/apache/commons/lang3/ArrayUtilsInsertTest.java b/src/test/java/org/apache/commons/lang3/ArrayUtilsInsertTest.java new file mode 100644 index 0000000..0c06c1f --- /dev/null +++ b/src/test/java/org/apache/commons/lang3/ArrayUtilsInsertTest.java @@ -0,0 +1,349 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package org.apache.commons.lang3; + +import static org.junit.Assert.*; + +import org.junit.Test; + +/** + * Tests ArrayUtils insert methods. + */ +public class ArrayUtilsInsertTest { + + @Test + public void testInsertBooleans() throws Exception { + final boolean[] array = {true,false,true}; + final boolean[] values = {false,true,false}; + + boolean[] result = ArrayUtils.insert(42, array, null); + assertArrayEquals(array, result); + assertFalse(array == result); + + assertNull(ArrayUtils.insert(42, null, array)); + assertArrayEquals(new boolean[0], ArrayUtils.insert(0, new boolean[0], null)); + assertNull(ArrayUtils.insert(42, (boolean[]) null, null)); + + try { + ArrayUtils.insert(-1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + try { + ArrayUtils.insert(array.length + 1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + assertArrayEquals(new boolean[]{false,true,false,true}, ArrayUtils.insert(0, array, false)); + assertArrayEquals(new boolean[]{true,false,false,true}, ArrayUtils.insert(1, array, false)); + assertArrayEquals(new boolean[]{true,false,true,false}, ArrayUtils.insert(array.length, array, false)); + assertArrayEquals(new boolean[]{false,true,false,true,false,true}, ArrayUtils.insert(0, array, values)); + assertArrayEquals(new boolean[]{true,false,true,false,false,true}, ArrayUtils.insert(1, array, values)); + assertArrayEquals(new boolean[]{true,false,true,false,true,false}, ArrayUtils.insert(array.length, array, values)); + } + + + @Test + public void testInsertBytes() throws Exception { + final byte[] array = {1,2,3}; + final byte[] values = {4,5,6}; + + byte[] result = ArrayUtils.insert(42, array, null); + assertArrayEquals(array, result); + assertFalse(array == result); + + assertNull(ArrayUtils.insert(42, null, array)); + assertArrayEquals(new byte[0], ArrayUtils.insert(0, new byte[0], null)); + assertNull(ArrayUtils.insert(42, (byte[]) null, null)); + + try { + ArrayUtils.insert(-1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + try { + ArrayUtils.insert(array.length + 1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + assertArrayEquals(new byte[]{0,1,2,3}, ArrayUtils.insert(0, array, (byte) 0)); + assertArrayEquals(new byte[]{1,0,2,3}, ArrayUtils.insert(1, array, (byte) 0)); + assertArrayEquals(new byte[]{1,2,3,0}, ArrayUtils.insert(array.length, array, (byte) 0)); + assertArrayEquals(new byte[]{4,5,6,1,2,3}, ArrayUtils.insert(0, array, values)); + assertArrayEquals(new byte[]{1,4,5,6,2,3}, ArrayUtils.insert(1, array, values)); + assertArrayEquals(new byte[]{1,2,3,4,5,6}, ArrayUtils.insert(array.length, array, values)); + } + + @Test + public void testInsertChars() throws Exception { + final char[] array = {'a','b','c'}; + final char[] values = {'d','e','f'}; + + char[] result = ArrayUtils.insert(42, array, null); + assertArrayEquals(array, result); + assertFalse(array == result); + + assertNull(ArrayUtils.insert(42, null, array)); + assertArrayEquals(new char[0], ArrayUtils.insert(0, new char[0], null)); + assertNull(ArrayUtils.insert(42, (char[]) null, null)); + + try { + ArrayUtils.insert(-1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + try { + ArrayUtils.insert(array.length + 1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + assertArrayEquals(new char[]{'z','a','b','c'}, ArrayUtils.insert(0, array, 'z')); + assertArrayEquals(new char[]{'a','z','b','c'}, ArrayUtils.insert(1, array, 'z')); + assertArrayEquals(new char[]{'a','b','c','z'}, ArrayUtils.insert(array.length, array, 'z')); + assertArrayEquals(new char[]{'d','e','f','a','b','c'}, ArrayUtils.insert(0, array, values)); + assertArrayEquals(new char[]{'a','d','e','f','b','c'}, ArrayUtils.insert(1, array, values)); + assertArrayEquals(new char[]{'a','b','c','d','e','f'}, ArrayUtils.insert(array.length, array, values)); + } + + @Test + public void testInsertDoubles() throws Exception { + final double[] array = {1,2,3}; + final double[] values = {4,5,6}; + final double delta = 0.000001; + + double[] result = ArrayUtils.insert(42, array, null); + assertArrayEquals(array, result, delta); + assertFalse(array == result); + + assertNull(ArrayUtils.insert(42, null, array)); + assertArrayEquals(new double[0], ArrayUtils.insert(0, new double[0], null), delta); + assertNull(ArrayUtils.insert(42, (double[]) null, null)); + + try { + ArrayUtils.insert(-1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + try { + ArrayUtils.insert(array.length + 1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + assertArrayEquals(new double[]{0,1,2,3}, ArrayUtils.insert(0, array, 0), delta); + assertArrayEquals(new double[]{1,0,2,3}, ArrayUtils.insert(1, array, 0), delta); + assertArrayEquals(new double[]{1,2,3,0}, ArrayUtils.insert(array.length, array, 0), delta); + assertArrayEquals(new double[]{4,5,6,1,2,3}, ArrayUtils.insert(0, array, values), delta); + assertArrayEquals(new double[]{1,4,5,6,2,3}, ArrayUtils.insert(1, array, values), delta); + assertArrayEquals(new double[]{1,2,3,4,5,6}, ArrayUtils.insert(array.length, array, values), delta); + } + + @Test + public void testInsertFloats() throws Exception { + final float[] array = {1,2,3}; + final float[] values = {4,5,6}; + final float delta = 0.000001f; + + float[] result = ArrayUtils.insert(42, array, null); + assertArrayEquals(array, result, delta); + assertFalse(array == result); + + assertNull(ArrayUtils.insert(42, null, array)); + assertArrayEquals(new float[0], ArrayUtils.insert(0, new float[0], null), delta); + assertNull(ArrayUtils.insert(42, (float[]) null, null)); + + try { + ArrayUtils.insert(-1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + try { + ArrayUtils.insert(array.length + 1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + assertArrayEquals(new float[]{0,1,2,3}, ArrayUtils.insert(0, array, 0), delta); + assertArrayEquals(new float[]{1,0,2,3}, ArrayUtils.insert(1, array, 0), delta); + assertArrayEquals(new float[]{1,2,3,0}, ArrayUtils.insert(array.length, array, 0), delta); + assertArrayEquals(new float[]{4,5,6,1,2,3}, ArrayUtils.insert(0, array, values), delta); + assertArrayEquals(new float[]{1,4,5,6,2,3}, ArrayUtils.insert(1, array, values), delta); + assertArrayEquals(new float[]{1,2,3,4,5,6}, ArrayUtils.insert(array.length, array, values), delta); + } + + @Test + public void testInsertInts() throws Exception { + final int[] array = {1,2,3}; + final int[] values = {4,5,6}; + + int[] result = ArrayUtils.insert(42, array, null); + assertArrayEquals(array, result); + assertFalse(array == result); + + assertNull(ArrayUtils.insert(42, null, array)); + assertArrayEquals(new int[0], ArrayUtils.insert(0, new int[0], null)); + assertNull(ArrayUtils.insert(42, (int[]) null, null)); + + try { + ArrayUtils.insert(-1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + try { + ArrayUtils.insert(array.length + 1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + assertArrayEquals(new int[]{0,1,2,3}, ArrayUtils.insert(0, array, 0)); + assertArrayEquals(new int[]{1,0,2,3}, ArrayUtils.insert(1, array, 0)); + assertArrayEquals(new int[]{1,2,3,0}, ArrayUtils.insert(array.length, array, 0)); + assertArrayEquals(new int[]{4,5,6,1,2,3}, ArrayUtils.insert(0, array, values)); + assertArrayEquals(new int[]{1,4,5,6,2,3}, ArrayUtils.insert(1, array, values)); + assertArrayEquals(new int[]{1,2,3,4,5,6}, ArrayUtils.insert(array.length, array, values)); + } + + + @Test + public void testInsertLongs() throws Exception { + final long[] array = {1,2,3}; + final long[] values = {4,5,6}; + + long[] result = ArrayUtils.insert(42, array, null); + assertArrayEquals(array, result); + assertFalse(array == result); + + assertNull(ArrayUtils.insert(42, null, array)); + assertArrayEquals(new long[0], ArrayUtils.insert(0, new long[0], null)); + assertNull(ArrayUtils.insert(42, (long[]) null, null)); + + try { + ArrayUtils.insert(-1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + try { + ArrayUtils.insert(array.length + 1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + assertArrayEquals(new long[]{0,1,2,3}, ArrayUtils.insert(0, array, 0)); + assertArrayEquals(new long[]{1,0,2,3}, ArrayUtils.insert(1, array, 0)); + assertArrayEquals(new long[]{1,2,3,0}, ArrayUtils.insert(array.length, array, 0)); + assertArrayEquals(new long[]{4,5,6,1,2,3}, ArrayUtils.insert(0, array, values)); + assertArrayEquals(new long[]{1,4,5,6,2,3}, ArrayUtils.insert(1, array, values)); + assertArrayEquals(new long[]{1,2,3,4,5,6}, ArrayUtils.insert(array.length, array, values)); + } + + + @Test + public void testInsertShorts() throws Exception { + final short[] array = {1,2,3}; + final short[] values = {4,5,6}; + + short[] result = ArrayUtils.insert(42, array, null); + assertArrayEquals(array, result); + assertFalse(array == result); + + assertNull(ArrayUtils.insert(42, null, array)); + assertArrayEquals(new short[0], ArrayUtils.insert(0, new short[0], null)); + assertNull(ArrayUtils.insert(42, (short[]) null, null)); + + try { + ArrayUtils.insert(-1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + try { + ArrayUtils.insert(array.length + 1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + assertArrayEquals(new short[]{0,1,2,3}, ArrayUtils.insert(0, array, (short) 0)); + assertArrayEquals(new short[]{1,0,2,3}, ArrayUtils.insert(1, array, (short) 0)); + assertArrayEquals(new short[]{1,2,3,0}, ArrayUtils.insert(array.length, array, (short) 0)); + assertArrayEquals(new short[]{4,5,6,1,2,3}, ArrayUtils.insert(0, array, values)); + assertArrayEquals(new short[]{1,4,5,6,2,3}, ArrayUtils.insert(1, array, values)); + assertArrayEquals(new short[]{1,2,3,4,5,6}, ArrayUtils.insert(array.length, array, values)); + } + + + @Test + public void testInsertGenericArray() throws Exception { + final String[] array = {"a","b","c"}; + final String[] values = {"d","e","f"}; + + String[] result = ArrayUtils.insert(42, array, (String[]) null); + assertArrayEquals(array, result); + assertFalse(array == result); + + assertNull(ArrayUtils.insert(42, null, array)); + assertArrayEquals(new String[0], ArrayUtils.insert(0, new String[0], (String[]) null)); + assertNull(ArrayUtils.insert(42, (String[]) null, (String[]) null)); + + try { + ArrayUtils.insert(-1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + try { + ArrayUtils.insert(array.length + 1, array, array); + fail("Expected IndexOutOfBoundsException"); + } catch (IndexOutOfBoundsException e) { + // expected + } + + assertArrayEquals(new String[]{"z","a","b","c"}, ArrayUtils.insert(0, array, "z")); + assertArrayEquals(new String[]{"a","z","b","c"}, ArrayUtils.insert(1, array, "z")); + assertArrayEquals(new String[]{"a","b","c","z"}, ArrayUtils.insert(array.length, array, "z")); + assertArrayEquals(new String[]{"d","e","f","a","b","c"}, ArrayUtils.insert(0, array, values)); + assertArrayEquals(new String[]{"a","d","e","f","b","c"}, ArrayUtils.insert(1, array, values)); + assertArrayEquals(new String[]{"a","b","c","d","e","f"}, ArrayUtils.insert(array.length, array, values)); + } +}