• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * ProGuard -- shrinking, optimization, obfuscation, and preverification
3  *             of Java bytecode.
4  *
5  * Copyright (c) 2002-2014 Eric Lafortune (eric@graphics.cornell.edu)
6  *
7  * This program is free software; you can redistribute it and/or modify it
8  * under the terms of the GNU General Public License as published by the Free
9  * Software Foundation; either version 2 of the License, or (at your option)
10  * any later version.
11  *
12  * This program is distributed in the hope that it will be useful, but WITHOUT
13  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
14  * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
15  * more details.
16  *
17  * You should have received a copy of the GNU General Public License along
18  * with this program; if not, write to the Free Software Foundation, Inc.,
19  * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20  */
21 package proguard.util;
22 
23 import java.lang.reflect.Array;
24 import java.util.Arrays;
25 
26 /**
27  * This class contains utility methods operating on arrays.
28  */
29 public class ArrayUtil
30 {
31     /**
32      * Returns whether the elements of the two given arrays are the same.
33      * @param array1 the first array.
34      * @param array2 the second array.
35      * @param size   the size of the arrays to be checked.
36      * @return whether the elements are the same.
37      */
equal(byte[] array1, byte[] array2, int size)38     public static boolean equal(byte[] array1, byte[] array2, int size)
39     {
40         for (int index = 0; index < size; index++)
41         {
42             if (array1[index] != array2[index])
43             {
44                 return false;
45             }
46         }
47 
48         return true;
49     }
50 
51 
52     /**
53      * Returns whether the elements of the two given arrays are the same.
54      * @param array1 the first array.
55      * @param array2 the second array.
56      * @param size   the size of the arrays to be checked.
57      * @return whether the elements are the same.
58      */
equal(short[] array1, short[] array2, int size)59     public static boolean equal(short[] array1, short[] array2, int size)
60     {
61         for (int index = 0; index < size; index++)
62         {
63             if (array1[index] != array2[index])
64             {
65                 return false;
66             }
67         }
68 
69         return true;
70     }
71 
72 
73     /**
74      * Returns whether the elements of the two given arrays are the same.
75      * @param array1 the first array.
76      * @param array2 the second array.
77      * @param size   the size of the arrays to be checked.
78      * @return whether the elements are the same.
79      */
equal(int[] array1, int[] array2, int size)80     public static boolean equal(int[] array1, int[] array2, int size)
81     {
82         for (int index = 0; index < size; index++)
83         {
84             if (array1[index] != array2[index])
85             {
86                 return false;
87             }
88         }
89 
90         return true;
91     }
92 
93 
94     /**
95      * Returns whether the elements of the two given arrays are the same.
96      * @param array1 the first array.
97      * @param array2 the second array.
98      * @param size   the size of the arrays to be checked.
99      * @return whether the elements are the same.
100      */
equal(Object[] array1, Object[] array2, int size)101     public static boolean equal(Object[] array1, Object[] array2, int size)
102     {
103         for (int index = 0; index < size; index++)
104         {
105             if (!array1[index].equals(array2[index]))
106             {
107                 return false;
108             }
109         }
110 
111         return true;
112     }
113 
114 
115     /**
116      * Returns whether the elements of the two given arrays are the same, or
117      * both arrays are null.
118      * @param array1 the first array.
119      * @param array2 the second array.
120      * @return whether the elements are the same.
121      */
equalOrNull(Object[] array1, Object[] array2)122     public static boolean equalOrNull(Object[] array1, Object[] array2)
123     {
124         return array1 == null ? array2 == null :
125             equalOrNull(array1, array2, array1.length);
126     }
127 
128 
129     /**
130      * Returns whether the elements of the two given arrays are the same, or
131      * both arrays are null.
132      * @param array1 the first array.
133      * @param array2 the second array.
134      * @param size   the size of the arrays to be checked.
135      * @return whether the elements are the same.
136      */
equalOrNull(Object[] array1, Object[] array2, int size)137     public static boolean equalOrNull(Object[] array1, Object[] array2, int size)
138     {
139         return array1 == null ? array2 == null :
140             array2 != null &&
141             equal(array1, array2, size);
142     }
143 
144 
145     /**
146      * Returns a hash code for the elements of the given array.
147      * @param array the array.
148      * @param size  the size of the array to be taken into account.
149      * @return a hash code.
150      */
hashCode(byte[] array, int size)151     public static int hashCode(byte[] array, int size)
152     {
153         int hashCode = 0;
154 
155         for (int index = 0; index < size; index++)
156         {
157             hashCode ^= array[index];
158         }
159 
160         return hashCode;
161     }
162 
163 
164     /**
165      * Returns a hash code for the elements of the given array.
166      * @param array the array.
167      * @param size  the size of the array to be taken into account.
168      * @return a hash code.
169      */
hashCode(short[] array, int size)170     public static int hashCode(short[] array, int size)
171     {
172         int hashCode = 0;
173 
174         for (int index = 0; index < size; index++)
175         {
176             hashCode ^= array[index];
177         }
178 
179         return hashCode;
180     }
181 
182 
183     /**
184      * Returns a hash code for the elements of the given array.
185      * @param array the array.
186      * @param size  the size of the array to be taken into account.
187      * @return a hash code.
188      */
hashCode(int[] array, int size)189     public static int hashCode(int[] array, int size)
190     {
191         int hashCode = 0;
192 
193         for (int index = 0; index < size; index++)
194         {
195             hashCode ^= array[index];
196         }
197 
198         return hashCode;
199     }
200 
201 
202     /**
203      * Returns a hash code for the elements of the given array.
204      * @param array the array.
205      * @param size  the size of the array to be taken into account.
206      * @return a hash code.
207      */
hashCode(Object[] array, int size)208     public static int hashCode(Object[] array, int size)
209     {
210         int hashCode = 0;
211 
212         for (int index = 0; index < size; index++)
213         {
214             hashCode ^= array[index].hashCode();
215         }
216 
217         return hashCode;
218     }
219 
220 
221     /**
222      * Returns a hash code for the elements of the given array, or 0 if it is
223      * null.
224      * @param array the array.
225      * @return a hash code.
226      */
hashCodeOrNull(Object[] array)227     public static int hashCodeOrNull(Object[] array)
228     {
229         return array == null ? 0 : hashCode(array, array.length);
230     }
231 
232 
233     /**
234      * Returns a hash code for the elements of the given array, or 0 if it is
235      * null.
236      * @param array the array.
237      * @param size  the size of the array to be taken into account.
238      * @return a hash code.
239      */
hashCodeOrNull(Object[] array, int size)240     public static int hashCodeOrNull(Object[] array, int size)
241     {
242         return array == null ? 0 : hashCode(array, size);
243     }
244 
245 
246     /**
247      * Compares the elements of the two given arrays.
248      * @param array1 the first array.
249      * @param size1  the size of the first array.
250      * @param array2 the second array.
251      * @param size2  the size of the second array.
252      * @return 0 if all elements are the same,
253      *          -1 if the first different element in the first array is smaller
254      *          than the corresponding element in the second array,
255      *          or 1 if it is larger.
256      */
compare(byte[] array1, int size1, byte[] array2, int size2)257     public static int compare(byte[] array1, int size1,
258                               byte[] array2, int size2)
259     {
260         int minSize = Math.min(size1, size2);
261 
262         for (int index = 0; index < minSize; index++)
263         {
264             if (array1[index] < array2[index])
265             {
266                 return -1;
267             }
268             else if (array1[index] > array2[index])
269             {
270                 return 1;
271             }
272         }
273 
274         return size1 <  size2 ? -1 :
275                size1 == size2 ?  0 :
276                                  1;
277     }
278 
279 
280     /**
281      * Compares the elements of the two given arrays.
282      * @param array1 the first array.
283      * @param size1  the size of the first array.
284      * @param array2 the second array.
285      * @param size2  the size of the second array.
286      * @return 0 if all elements are the same,
287      *          -1 if the first different element in the first array is smaller
288      *          than the corresponding element in the second array,
289      *          or 1 if it is larger.
290      */
compare(short[] array1, int size1, short[] array2, int size2)291     public static int compare(short[] array1, int size1,
292                               short[] array2, int size2)
293     {
294         int minSize = Math.min(size1, size2);
295 
296         for (int index = 0; index < minSize; index++)
297         {
298             if (array1[index] < array2[index])
299             {
300                 return -1;
301             }
302             else if (array1[index] > array2[index])
303             {
304                 return 1;
305             }
306         }
307 
308         return size1 <  size2 ? -1 :
309                size1 == size2 ?  0 :
310                                  1;
311     }
312 
313 
314     /**
315      * Compares the elements of the two given arrays.
316      * @param array1 the first array.
317      * @param size1  the size of the first array.
318      * @param array2 the second array.
319      * @param size2  the size of the second array.
320      * @return 0 if all elements are the same,
321      *          -1 if the first different element in the first array is smaller
322      *          than the corresponding element in the second array,
323      *          or 1 if it is larger.
324      */
compare(int[] array1, int size1, int[] array2, int size2)325     public static int compare(int[] array1, int size1,
326                               int[] array2, int size2)
327     {
328         int minSize = Math.min(size1, size2);
329 
330         for (int index = 0; index < minSize; index++)
331         {
332             if (array1[index] < array2[index])
333             {
334                 return -1;
335             }
336             else if (array1[index] > array2[index])
337             {
338                 return 1;
339             }
340         }
341 
342         return size1 <  size2 ? -1 :
343                size1 == size2 ?  0 :
344                                  1;
345     }
346 
347 
348     /**
349      * Compares the elements of the two given arrays.
350      * @param array1 the first array.
351      * @param size1  the size of the first array.
352      * @param array2 the second array.
353      * @param size2  the size of the second array.
354      * @return 0 if all elements are the same,
355      *          -1 if the first different element in the first array is smaller
356      *          than the corresponding element in the second array,
357      *          or 1 if it is larger.
358      */
compare(Comparable[] array1, int size1, Comparable[] array2, int size2)359     public static int compare(Comparable[] array1, int size1,
360                               Comparable[] array2, int size2)
361     {
362         int minSize = Math.min(size1, size2);
363 
364         for (int index = 0; index < minSize; index++)
365         {
366             int comparison = ObjectUtil.compare(array1[index], array2[index]);
367             if (comparison != 0)
368             {
369                 return comparison;
370             }
371         }
372 
373         return size1 <  size2 ? -1 :
374                size1 == size2 ?  0 :
375                                  1;
376     }
377 
378 
379     /**
380      * Ensures the given array has a given size.
381      * @param array the array.
382      * @param size  the target size of the array.
383      * @return      the original array, or a copy if it had to be extended.
384      */
extendArray(boolean[] array, int size)385     public static boolean[] extendArray(boolean[] array, int size)
386     {
387         // Reuse the existing array if possible.
388         if (array.length >= size)
389         {
390             return array;
391         }
392 
393         // Otherwise create and initialize a new array.
394         boolean[] newArray = new boolean[size];
395 
396         System.arraycopy(array, 0,
397                          newArray, 0,
398                          array.length);
399 
400         return newArray;
401     }
402 
403 
404     /**
405      * Ensures the given array has a given size.
406      * @param array        the array.
407      * @param size         the target size of the array.
408      * @param initialValue the initial value of the elements.
409      * @return             the original array, or a copy if it had to be
410      *                     extended.
411      */
ensureArraySize(boolean[] array, int size, boolean initialValue)412     public static boolean[] ensureArraySize(boolean[] array,
413                                             int       size,
414                                             boolean   initialValue)
415     {
416         // Is the existing array large enough?
417         if (array.length >= size)
418         {
419             // Reinitialize the existing array.
420             Arrays.fill(array, 0, size, initialValue);
421         }
422         else
423         {
424             // Otherwise create and initialize a new array.
425             array = new boolean[size];
426 
427             if (initialValue)
428             {
429                 Arrays.fill(array, 0, size, initialValue);
430             }
431         }
432 
433         return array;
434     }
435 
436 
437     /**
438      * Adds the given element to the given array.
439      * The array is extended if necessary.
440      * @param array   the array.
441      * @param size    the original size of the array.
442      * @param element the element to be added.
443      * @return        the original array, or a copy if it had to be extended.
444      */
add(byte[] array, int size, byte element)445     public static byte[] add(byte[] array, int size, byte element)
446     {
447         array = extendArray(array, size + 1);
448 
449         array[size] = element;
450 
451         return array;
452     }
453 
454 
455     /**
456      * Inserts the given element in the given array.
457      * The array is extended if necessary.
458      * @param array   the array.
459      * @param size    the original size of the array.
460      * @param index   the index at which the element is to be added.
461      * @param element the element to be added.
462      * @return        the original array, or a copy if it had to be extended.
463      */
insert(byte[] array, int size, int index, byte element)464     public static byte[] insert(byte[] array, int size, int index, byte element)
465     {
466         array = extendArray(array, size + 1);
467 
468         // Move the last part.
469         System.arraycopy(array, index,
470                          array, index + 1,
471                          size - index);
472 
473         array[index] = element;
474 
475         return array;
476     }
477 
478 
479     /**
480      * Removes the specified element from the given array.
481      * @param array the array.
482      * @param size  the original size of the array.
483      * @param index the index of the element to be removed.
484      */
remove(byte[] array, int size, int index)485     public static void remove(byte[] array, int size, int index)
486     {
487         System.arraycopy(array, index + 1,
488                          array, index,
489                          array.length - index - 1);
490 
491         array[size - 1] = 0;
492     }
493 
494 
495     /**
496      * Ensures the given array has a given size.
497      * @param array the array.
498      * @param size  the target size of the array.
499      * @return      the original array, or a copy if it had to be extended.
500      */
extendArray(byte[] array, int size)501     public static byte[] extendArray(byte[] array, int size)
502     {
503         // Reuse the existing array if possible.
504         if (array.length >= size)
505         {
506             return array;
507         }
508 
509         // Otherwise create and initialize a new array.
510         byte[] newArray = new byte[size];
511 
512         System.arraycopy(array, 0,
513                          newArray, 0,
514                          array.length);
515 
516         return newArray;
517     }
518 
519 
520     /**
521      * Ensures the given array has a given size.
522      * @param array        the array.
523      * @param size         the target size of the array.
524      * @param initialValue the initial value of the elements.
525      * @return             the original array, or a copy if it had to be
526      *                     extended.
527      */
ensureArraySize(byte[] array, int size, byte initialValue)528     public static byte[] ensureArraySize(byte[] array,
529                                          int    size,
530                                          byte   initialValue)
531     {
532         // Is the existing array large enough?
533         if (array.length >= size)
534         {
535             // Reinitialize the existing array.
536             Arrays.fill(array, 0, size, initialValue);
537         }
538         else
539         {
540             // Otherwise create and initialize a new array.
541             array = new byte[size];
542 
543             if (initialValue != 0)
544             {
545                 Arrays.fill(array, 0, size, initialValue);
546             }
547         }
548 
549         return array;
550     }
551 
552 
553     /**
554      * Adds the given element to the given array.
555      * The array is extended if necessary.
556      * @param array   the array.
557      * @param size    the original size of the array.
558      * @param element the element to be added.
559      * @return        the original array, or a copy if it had to be extended.
560      */
add(short[] array, int size, short element)561     public static short[] add(short[] array, int size, short element)
562     {
563         array = extendArray(array, size + 1);
564 
565         array[size] = element;
566 
567         return array;
568     }
569 
570 
571     /**
572      * Inserts the given element in the given array.
573      * The array is extended if necessary.
574      * @param array   the array.
575      * @param size    the original size of the array.
576      * @param index   the index at which the element is to be added.
577      * @param element the element to be added.
578      * @return        the original array, or a copy if it had to be extended.
579      */
insert(short[] array, int size, int index, short element)580     public static short[] insert(short[] array, int size, int index, short element)
581     {
582         array = extendArray(array, size + 1);
583 
584         // Move the last part.
585         System.arraycopy(array, index,
586                          array, index + 1,
587                          size - index);
588 
589         array[index] = element;
590 
591         return array;
592     }
593 
594 
595     /**
596      * Removes the specified element from the given array.
597      * @param array the array.
598      * @param size  the original size of the array.
599      * @param index the index of the element to be removed.
600      */
remove(short[] array, int size, int index)601     public static void remove(short[] array, int size, int index)
602     {
603         System.arraycopy(array, index + 1,
604                          array, index,
605                          array.length - index - 1);
606 
607         array[size - 1] = 0;
608     }
609 
610 
611     /**
612      * Ensures the given array has a given size.
613      * @param array the array.
614      * @param size  the target size of the array.
615      * @return      the original array, or a copy if it had to be extended.
616      */
extendArray(short[] array, int size)617     public static short[] extendArray(short[] array, int size)
618     {
619         // Reuse the existing array if possible.
620         if (array.length >= size)
621         {
622             return array;
623         }
624 
625         // Otherwise create and initialize a new array.
626         short[] newArray = new short[size];
627 
628         System.arraycopy(array, 0,
629                          newArray, 0,
630                          array.length);
631 
632         return newArray;
633     }
634 
635 
636     /**
637      * Ensures the given array has a given size.
638      * @param array        the array.
639      * @param size         the target size of the array.
640      * @param initialValue the initial value of the elements.
641      * @return             the original array, or a copy if it had to be
642      *                     extended.
643      */
ensureArraySize(short[] array, int size, short initialValue)644     public static short[] ensureArraySize(short[] array,
645                                           int     size,
646                                           short   initialValue)
647     {
648         // Is the existing array large enough?
649         if (array.length >= size)
650         {
651             // Reinitialize the existing array.
652             Arrays.fill(array, 0, size, initialValue);
653         }
654         else
655         {
656             // Otherwise create and initialize a new array.
657             array = new short[size];
658 
659             if (initialValue != 0)
660             {
661                 Arrays.fill(array, 0, size, initialValue);
662             }
663         }
664 
665         return array;
666     }
667 
668 
669     /**
670      * Adds the given element to the given array.
671      * The array is extended if necessary.
672      * @param array   the array.
673      * @param size    the original size of the array.
674      * @param element the element to be added.
675      * @return        the original array, or a copy if it had to be extended.
676      */
add(int[] array, int size, int element)677     public static int[] add(int[] array, int size, int element)
678     {
679         array = extendArray(array, size + 1);
680 
681         array[size] = element;
682 
683         return array;
684     }
685 
686 
687     /**
688      * Inserts the given element in the given array.
689      * The array is extended if necessary.
690      * @param array   the array.
691      * @param size    the original size of the array.
692      * @param index   the index at which the element is to be added.
693      * @param element the element to be added.
694      * @return        the original array, or a copy if it had to be extended.
695      */
insert(int[] array, int size, int index, int element)696     public static int[] insert(int[] array, int size, int index, int element)
697     {
698         array = extendArray(array, size + 1);
699 
700         // Move the last part.
701         System.arraycopy(array, index,
702                          array, index + 1,
703                          size - index);
704 
705         array[index] = element;
706 
707         return array;
708     }
709 
710 
711     /**
712      * Removes the specified element from the given array.
713      * @param array the array.
714      * @param size  the original size of the array.
715      * @param index the index of the element to be removed.
716      */
remove(int[] array, int size, int index)717     public static void remove(int[] array, int size, int index)
718     {
719         System.arraycopy(array, index + 1,
720                          array, index,
721                          array.length - index - 1);
722 
723         array[size - 1] = 0;
724     }
725 
726 
727     /**
728      * Ensures the given array has a given size.
729      * @param array the array.
730      * @param size  the target size of the array.
731      * @return      the original array, or a copy if it had to be extended.
732      */
extendArray(int[] array, int size)733     public static int[] extendArray(int[] array, int size)
734     {
735         // Reuse the existing array if possible.
736         if (array.length >= size)
737         {
738             return array;
739         }
740 
741         // Otherwise create and initialize a new array.
742         int[] newArray = new int[size];
743 
744         System.arraycopy(array, 0,
745                          newArray, 0,
746                          array.length);
747 
748         return newArray;
749     }
750 
751 
752     /**
753      * Ensures the given array has a given size.
754      * @param array        the array.
755      * @param size         the target size of the array.
756      * @param initialValue the initial value of the elements.
757      * @return             the original array, or a copy if it had to be
758      *                     extended.
759      */
ensureArraySize(int[] array, int size, int initialValue)760     public static int[] ensureArraySize(int[] array,
761                                         int   size,
762                                         int   initialValue)
763     {
764         // Is the existing array large enough?
765         if (array.length >= size)
766         {
767             // Reinitialize the existing array.
768             Arrays.fill(array, 0, size, initialValue);
769         }
770         else
771         {
772             // Otherwise create and initialize a new array.
773             array = new int[size];
774 
775             if (initialValue != 0)
776             {
777                 Arrays.fill(array, 0, size, initialValue);
778             }
779         }
780 
781         return array;
782     }
783 
784 
785     /**
786      * Adds the given element to the given array.
787      * The array is extended if necessary.
788      * @param array   the array.
789      * @param size    the original size of the array.
790      * @param element the element to be added.
791      * @return        the original array, or a copy if it had to be extended.
792      */
add(long[] array, int size, long element)793     public static long[] add(long[] array, int size, long element)
794     {
795         array = extendArray(array, size + 1);
796 
797         array[size] = element;
798 
799         return array;
800     }
801 
802 
803     /**
804      * Inserts the given element in the given array.
805      * The array is extended if necessary.
806      * @param array   the array.
807      * @param size    the original size of the array.
808      * @param index   the index at which the element is to be added.
809      * @param element the element to be added.
810      * @return        the original array, or a copy if it had to be extended.
811      */
insert(long[] array, int size, int index, long element)812     public static long[] insert(long[] array, int size, int index, long element)
813     {
814         array = extendArray(array, size + 1);
815 
816         // Move the last part.
817         System.arraycopy(array, index,
818                          array, index + 1,
819                          size - index);
820 
821         array[index] = element;
822 
823         return array;
824     }
825 
826 
827     /**
828      * Removes the specified element from the given array.
829      * @param array the array.
830      * @param size  the original size of the array.
831      * @param index the index of the element to be removed.
832      */
remove(long[] array, int size, int index)833     public static void remove(long[] array, int size, int index)
834     {
835         System.arraycopy(array, index + 1,
836                          array, index,
837                          array.length - index - 1);
838 
839         array[size - 1] = 0;
840     }
841 
842 
843     /**
844      * Ensures the given array has a given size.
845      * @param array the array.
846      * @param size  the target size of the array.
847      * @return      the original array, or a copy if it had to be extended.
848      */
extendArray(long[] array, int size)849     public static long[] extendArray(long[] array, int size)
850     {
851         // Reuse the existing array if possible.
852         if (array.length >= size)
853         {
854             return array;
855         }
856 
857         // Otherwise create and initialize a new array.
858         long[] newArray = new long[size];
859 
860         System.arraycopy(array, 0,
861                          newArray, 0,
862                          array.length);
863 
864         return newArray;
865     }
866 
867 
868     /**
869      * Ensures the given array has a given size.
870      * @param array        the array.
871      * @param size         the target size of the array.
872      * @param initialValue the initial value of the elements.
873      * @return             the original array, or a copy if it had to be
874      *                     extended.
875      */
ensureArraySize(long[] array, int size, long initialValue)876     public static long[] ensureArraySize(long[] array,
877                                          int    size,
878                                          long   initialValue)
879     {
880         // Is the existing array large enough?
881         if (array.length >= size)
882         {
883             // Reinitialize the existing array.
884             Arrays.fill(array, 0, size, initialValue);
885         }
886         else
887         {
888             // Otherwise create and initialize a new array.
889             array = new long[size];
890 
891             if (initialValue != 0L)
892             {
893                 Arrays.fill(array, 0, size, initialValue);
894             }
895         }
896 
897         return array;
898     }
899 
900 
901     /**
902      * Adds the given element to the given array.
903      * The array is extended if necessary.
904      * @param array   the array.
905      * @param size    the original size of the array.
906      * @param element the element to be added.
907      * @return        the original array, or a copy if it had to be extended.
908      */
add(Object[] array, int size, Object element)909     public static Object[] add(Object[] array, int size, Object element)
910     {
911         array = extendArray(array, size + 1);
912 
913         array[size] = element;
914 
915         return array;
916     }
917 
918 
919     /**
920      * Inserts the given element in the given array.
921      * The array is extended if necessary.
922      * @param array   the array.
923      * @param size    the original size of the array.
924      * @param index   the index at which the element is to be added.
925      * @param element the element to be added.
926      * @return        the original array, or a copy if it had to be extended.
927      */
insert(Object[] array, int size, int index, Object element)928     public static Object[] insert(Object[] array, int size, int index, Object element)
929     {
930         array = extendArray(array, size + 1);
931 
932         // Move the last part.
933         System.arraycopy(array, index,
934                          array, index + 1,
935                          size - index);
936 
937         array[index] = element;
938 
939         return array;
940     }
941 
942 
943     /**
944      * Removes the specified element from the given array.
945      * @param array the array.
946      * @param size  the original size of the array.
947      * @param index the index of the element to be removed.
948      */
remove(Object[] array, int size, int index)949     public static void remove(Object[] array, int size, int index)
950     {
951         System.arraycopy(array, index + 1,
952                          array, index,
953                          array.length - index - 1);
954 
955         array[size - 1] = null;
956     }
957 
958 
959     /**
960      * Ensures the given array has a given size.
961      * @param array the array.
962      * @param size  the target size of the array.
963      * @return      the original array, or a copy if it had to be extended.
964      */
extendArray(Object[] array, int size)965     public static Object[] extendArray(Object[] array, int size)
966     {
967         // Reuse the existing array if possible.
968         if (array.length >= size)
969         {
970             return array;
971         }
972 
973         // Otherwise create and initialize a new array.
974         Object[] newArray = (Object[])Array.newInstance(array.getClass().getComponentType(), size);
975 
976         System.arraycopy(array, 0,
977                          newArray, 0,
978                          array.length);
979 
980         return newArray;
981     }
982 
983 
984     /**
985      * Ensures the given array has a given size.
986      * @param array        the array.
987      * @param size         the target size of the array.
988      * @param initialValue the initial value of the elements.
989      * @return             the original array, or a copy if it had to be
990      *                     extended.
991      */
ensureArraySize(Object[] array, int size, Object initialValue)992     public static Object[] ensureArraySize(Object[] array,
993                                            int      size,
994                                            Object   initialValue)
995     {
996         // Is the existing array large enough?
997         if (array.length >= size)
998         {
999             // Reinitialize the existing array.
1000             Arrays.fill(array, 0, size, initialValue);
1001         }
1002         else
1003         {
1004             // Otherwise create and initialize a new array.
1005             array = (Object[])Array.newInstance(array.getClass().getComponentType(), size);
1006 
1007             if (initialValue != null)
1008             {
1009                 Arrays.fill(array, 0, size, initialValue);
1010             }
1011         }
1012 
1013         return array;
1014     }
1015 }
1016