001/*
002 * Copyright 2010-2015 Institut Pasteur.
003 * 
004 * This file is part of Icy.
005 * 
006 * Icy is free software: you can redistribute it and/or modify
007 * it under the terms of the GNU General Public License as published by
008 * the Free Software Foundation, either version 3 of the License, or
009 * (at your option) any later version.
010 * 
011 * Icy is distributed in the hope that it will be useful,
012 * but WITHOUT ANY WARRANTY; without even the implied warranty of
013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
014 * GNU General Public License for more details.
015 * 
016 * You should have received a copy of the GNU General Public License
017 * along with Icy. If not, see <http://www.gnu.org/licenses/>.
018 */
019package icy.type.collection.array;
020
021import icy.math.MathUtil;
022import icy.type.DataType;
023import icy.type.TypeUtil;
024import icy.util.StringUtil;
025
026import java.awt.Dimension;
027import java.awt.Point;
028import java.awt.Rectangle;
029import java.lang.reflect.Array;
030import java.util.Arrays;
031
032/**
033 * @author Stephane
034 */
035public class Array1DUtil
036{
037    /**
038     * Return the total number of element of the specified array
039     */
040    public static int getTotalLength(byte[] array)
041    {
042        if (array != null)
043            return array.length;
044
045        return 0;
046    }
047
048    /**
049     * Return the total number of element of the specified array
050     */
051    public static int getTotalLength(short[] array)
052    {
053        if (array != null)
054            return array.length;
055
056        return 0;
057    }
058
059    /**
060     * Return the total number of element of the specified array
061     */
062    public static int getTotalLength(int[] array)
063    {
064        if (array != null)
065            return array.length;
066
067        return 0;
068    }
069
070    /**
071     * Return the total number of element of the specified array
072     */
073    public static int getTotalLength(long[] array)
074    {
075        if (array != null)
076            return array.length;
077
078        return 0;
079    }
080
081    /**
082     * Return the total number of element of the specified array
083     */
084    public static int getTotalLength(float[] array)
085    {
086        if (array != null)
087            return array.length;
088
089        return 0;
090    }
091
092    /**
093     * Return the total number of element of the specified array
094     */
095    public static int getTotalLength(double[] array)
096    {
097        if (array != null)
098            return array.length;
099
100        return 0;
101    }
102
103    /**
104     * @deprecated
105     *             use {@link #getTotalLength(byte[])} instead
106     */
107    @Deprecated
108    public static int getTotalLenght(byte[] array)
109    {
110        return getTotalLength(array);
111    }
112
113    /**
114     * @deprecated
115     *             use {@link #getTotalLength(short[])} instead
116     */
117    @Deprecated
118    public static int getTotalLenght(short[] array)
119    {
120        return getTotalLength(array);
121    }
122
123    /**
124     * @deprecated
125     *             use {@link #getTotalLength(int[])} instead
126     */
127    @Deprecated
128    public static int getTotalLenght(int[] array)
129    {
130        return getTotalLength(array);
131    }
132
133    /**
134     * @deprecated
135     *             use {@link #getTotalLength(float[])} instead
136     */
137    @Deprecated
138    public static int getTotalLenght(float[] array)
139    {
140        return getTotalLength(array);
141    }
142
143    /**
144     * @deprecated
145     *             use {@link #getTotalLength(double[])} instead
146     */
147    @Deprecated
148    public static int getTotalLenght(double[] array)
149    {
150        return getTotalLength(array);
151    }
152
153    /**
154     * Create a new 1D array with specified data type and length
155     */
156    public static Object createArray(DataType dataType, int len)
157    {
158        switch (dataType.getJavaType())
159        {
160            case BYTE:
161                return new byte[len];
162            case SHORT:
163                return new short[len];
164            case INT:
165                return new int[len];
166            case LONG:
167                return new long[len];
168            case FLOAT:
169                return new float[len];
170            case DOUBLE:
171                return new double[len];
172            default:
173                return null;
174        }
175    }
176
177    /**
178     * Create a new 1D array with specified data type and length
179     * 
180     * @deprecated use {@link #createArray(DataType, int)} instead
181     */
182    @Deprecated
183    public static Object createArray(int dataType, int len)
184    {
185        return createArray(DataType.getDataType(dataType), len);
186    }
187
188    /**
189     * Allocate the specified 1D array if it's defined to null with the specified len
190     */
191    public static Object allocIfNull(Object out, DataType dataType, int len)
192    {
193        if (out == null)
194        {
195            switch (dataType.getJavaType())
196            {
197                case BYTE:
198                    return new byte[len];
199                case SHORT:
200                    return new short[len];
201                case INT:
202                    return new int[len];
203                case LONG:
204                    return new long[len];
205                case FLOAT:
206                    return new float[len];
207                case DOUBLE:
208                    return new double[len];
209            }
210        }
211
212        return out;
213    }
214
215    /**
216     * Allocate the specified array if it's defined to null with the specified len
217     */
218    public static boolean[] allocIfNull(boolean[] out, int len)
219    {
220        if (out == null)
221            return new boolean[len];
222
223        return out;
224    }
225
226    /**
227     * Allocate the specified array if it's defined to null with the specified len
228     */
229    public static byte[] allocIfNull(byte[] out, int len)
230    {
231        if (out == null)
232            return new byte[len];
233
234        return out;
235    }
236
237    /**
238     * Allocate the specified array if it's defined to null with the specified len
239     */
240    public static short[] allocIfNull(short[] out, int len)
241    {
242        if (out == null)
243            return new short[len];
244
245        return out;
246    }
247
248    /**
249     * Allocate the specified array if it's defined to null with the specified len
250     */
251    public static int[] allocIfNull(int[] out, int len)
252    {
253        if (out == null)
254            return new int[len];
255
256        return out;
257    }
258
259    /**
260     * Allocate the specified array if it's defined to null with the specified len
261     */
262    public static long[] allocIfNull(long[] out, int len)
263    {
264        if (out == null)
265            return new long[len];
266
267        return out;
268    }
269
270    /**
271     * Allocate the specified array if it's defined to null with the specified len
272     */
273    public static float[] allocIfNull(float[] out, int len)
274    {
275        if (out == null)
276            return new float[len];
277
278        return out;
279    }
280
281    /**
282     * Allocate the specified array if it's defined to null with the specified lenght
283     */
284    public static double[] allocIfNull(double[] out, int len)
285    {
286        if (out == null)
287            return new double[len];
288
289        return out;
290    }
291
292    /**
293     * Do a copy of the specified array
294     */
295    public static Object copyOf(Object array)
296    {
297        switch (ArrayUtil.getDataType(array))
298        {
299            case BYTE:
300                return Arrays.copyOf((byte[]) array, ((byte[]) array).length);
301            case SHORT:
302                return Arrays.copyOf((short[]) array, ((short[]) array).length);
303            case INT:
304                return Arrays.copyOf((int[]) array, ((int[]) array).length);
305            case LONG:
306                return Arrays.copyOf((long[]) array, ((long[]) array).length);
307            case FLOAT:
308                return Arrays.copyOf((float[]) array, ((float[]) array).length);
309            case DOUBLE:
310                return Arrays.copyOf((double[]) array, ((double[]) array).length);
311            default:
312                return null;
313        }
314    }
315
316    //
317    //
318    //
319    //
320
321    /**
322     * Get value as double from specified 1D array and offset.<br>
323     * If signed is true then any integer primitive is considered as signed data.
324     * Use {@link #getValue(Object, int, DataType)} we you know the DataType as it is faster.
325     */
326    public static double getValue(Object array, int offset, boolean signed)
327    {
328        return getValue(array, offset, ArrayUtil.getDataType(array, signed));
329    }
330
331    /**
332     * Get value as double from specified 1D array and offset.<br>
333     * Use specified DataType to case input array (no type check)
334     */
335    public static double getValue(Object array, int offset, DataType dataType)
336    {
337        switch (dataType)
338        {
339            case BYTE:
340                return getValue((byte[]) array, offset, true);
341            case UBYTE:
342                return getValue((byte[]) array, offset, false);
343            case SHORT:
344                return getValue((short[]) array, offset, true);
345            case USHORT:
346                return getValue((short[]) array, offset, false);
347            case INT:
348                return getValue((int[]) array, offset, true);
349            case UINT:
350                return getValue((int[]) array, offset, false);
351            case LONG:
352                return getValue((long[]) array, offset, true);
353            case ULONG:
354                return getValue((long[]) array, offset, false);
355            case FLOAT:
356                return getValue((float[]) array, offset);
357            case DOUBLE:
358                return getValue((double[]) array, offset);
359            default:
360                return 0d;
361        }
362    }
363
364    /**
365     * Get value as double from specified 1D array and offset.<br>
366     * If signed is true then any integer primitive is considered as signed data
367     * 
368     * @deprecated use {@link #getValue(Object, int, DataType)} instead
369     */
370    @Deprecated
371    public static double getValue(Object array, int offset, int dataType, boolean signed)
372    {
373        return getValue(array, offset, DataType.getDataType(dataType, signed));
374    }
375
376    /**
377     * Get value as float from specified 1D array and offset.<br>
378     * If signed is true then any integer primitive is considered as signed data
379     */
380    public static float getValueAsFloat(Object array, int offset, boolean signed)
381    {
382        return getValueAsFloat(array, offset, ArrayUtil.getDataType(array, signed));
383    }
384
385    /**
386     * Get value as float from specified 1D array and offset.<br>
387     * Use specified DataType to case input array (no type check)
388     */
389    public static float getValueAsFloat(Object array, int offset, DataType dataType)
390    {
391        switch (dataType)
392        {
393            case BYTE:
394                return getValueAsFloat((byte[]) array, offset, true);
395            case UBYTE:
396                return getValueAsFloat((byte[]) array, offset, false);
397            case SHORT:
398                return getValueAsFloat((short[]) array, offset, true);
399            case USHORT:
400                return getValueAsFloat((short[]) array, offset, false);
401            case INT:
402                return getValueAsFloat((int[]) array, offset, true);
403            case UINT:
404                return getValueAsFloat((int[]) array, offset, false);
405            case LONG:
406                return getValueAsFloat((long[]) array, offset, true);
407            case ULONG:
408                return getValueAsFloat((long[]) array, offset, false);
409            case FLOAT:
410                return getValueAsFloat((float[]) array, offset);
411            case DOUBLE:
412                return getValueAsFloat((double[]) array, offset);
413            default:
414                return 0;
415        }
416    }
417
418    /**
419     * Get value as float from specified 1D array and offset.<br>
420     * If signed is true then any integer primitive is considered as signed data
421     * 
422     * @deprecated use {@link #getValueAsFloat(Object, int, DataType)} instead
423     */
424    @Deprecated
425    public static float getValueAsFloat(Object array, int offset, int dataType, boolean signed)
426    {
427        return getValueAsFloat(array, offset, DataType.getDataType(dataType, signed));
428    }
429
430    /**
431     * Get value as integer from specified 1D array and offset.<br>
432     * If signed is true then any integer primitive is considered as signed data
433     */
434    public static int getValueAsInt(Object array, int offset, boolean signed)
435    {
436        return getValueAsInt(array, offset, ArrayUtil.getDataType(array, signed));
437    }
438
439    /**
440     * Get value as integer from specified 1D array and offset.<br>
441     * Use specified DataType to case input array (no type check)
442     */
443    public static int getValueAsInt(Object array, int offset, DataType dataType)
444    {
445        switch (dataType)
446        {
447            case BYTE:
448                return getValueAsInt((byte[]) array, offset, true);
449            case UBYTE:
450                return getValueAsInt((byte[]) array, offset, false);
451            case SHORT:
452                return getValueAsInt((short[]) array, offset, true);
453            case USHORT:
454                return getValueAsInt((short[]) array, offset, false);
455            case INT:
456            case UINT:
457                return getValueAsInt((int[]) array, offset);
458            case LONG:
459            case ULONG:
460                return getValueAsInt((long[]) array, offset);
461            case FLOAT:
462                return getValueAsInt((float[]) array, offset);
463            case DOUBLE:
464                return getValueAsInt((double[]) array, offset);
465            default:
466                return 0;
467        }
468    }
469
470    /**
471     * Get value as float from specified 1D array and offset.<br>
472     * If signed is true then any integer primitive is considered as signed data
473     * 
474     * @deprecated use {@link #getValueAsInt(Object, int, DataType)} instead
475     */
476    @Deprecated
477    public static int getValueAsInt(Object array, int offset, int dataType, boolean signed)
478    {
479        return getValueAsInt(array, offset, DataType.getDataType(dataType, signed));
480    }
481
482    /**
483     * Get value as integer from specified 1D array and offset.<br>
484     * If signed is true then any integer primitive is considered as signed data
485     */
486    public static long getValueAsLong(Object array, int offset, boolean signed)
487    {
488        return getValueAsLong(array, offset, ArrayUtil.getDataType(array, signed));
489    }
490
491    /**
492     * Get value as integer from specified 1D array and offset.<br>
493     * Use specified DataType to case input array (no type check)
494     */
495    public static long getValueAsLong(Object array, int offset, DataType dataType)
496    {
497        switch (dataType)
498        {
499            case BYTE:
500                return getValueAsLong((byte[]) array, offset, true);
501            case UBYTE:
502                return getValueAsLong((byte[]) array, offset, false);
503            case SHORT:
504                return getValueAsLong((short[]) array, offset, true);
505            case USHORT:
506                return getValueAsLong((short[]) array, offset, false);
507            case INT:
508                return getValueAsLong((int[]) array, offset, true);
509            case UINT:
510                return getValueAsLong((int[]) array, offset, false);
511            case LONG:
512            case ULONG:
513                return getValueAsLong((long[]) array, offset);
514            case FLOAT:
515                return getValueAsLong((float[]) array, offset);
516            case DOUBLE:
517                return getValueAsLong((double[]) array, offset);
518            default:
519                return 0;
520        }
521    }
522
523    /**
524     * Get value as float from specified 1D array and offset.<br>
525     * If signed is true then any integer primitive is considered as signed data
526     * 
527     * @deprecated use {@link #getValueAsLong(Object, int, DataType)} instead
528     */
529    @Deprecated
530    public static long getValueAsLong(Object array, int offset, int dataType, boolean signed)
531    {
532        return getValueAsLong(array, offset, DataType.getDataType(dataType, signed));
533    }
534
535    /**
536     * Set value at specified offset as double value.
537     */
538    public static void setValue(Object array, int offset, double value)
539    {
540        setValue(array, offset, ArrayUtil.getDataType(array), value);
541    }
542
543    /**
544     * Set value at specified offset as double value.
545     */
546    public static void setValue(Object array, int offset, DataType dataType, double value)
547    {
548        switch (dataType.getJavaType())
549        {
550            case BYTE:
551                setValue((byte[]) array, offset, value);
552                break;
553
554            case SHORT:
555                setValue((short[]) array, offset, value);
556                break;
557
558            case INT:
559                setValue((int[]) array, offset, value);
560                break;
561
562            case LONG:
563                setValue((long[]) array, offset, value);
564                break;
565
566            case FLOAT:
567                setValue((float[]) array, offset, value);
568                break;
569
570            case DOUBLE:
571                setValue((double[]) array, offset, value);
572                break;
573        }
574    }
575
576    /**
577     * Set value at specified offset as double value.
578     * 
579     * @deprecated use {@link #setValue(Object, int, DataType, double)} instead
580     */
581    @Deprecated
582    public static void setValue(Object array, int offset, int dataType, double value)
583    {
584        setValue(array, offset, DataType.getDataType(dataType), value);
585    }
586
587    /**
588     * Get value as double from specified byte array and offset.<br>
589     * If signed is true then we consider data as signed
590     */
591    public static double getValue(byte[] array, int offset, boolean signed)
592    {
593        return TypeUtil.toDouble(array[offset], signed);
594    }
595
596    /**
597     * Get value as double from specified short array and offset.<br>
598     * If signed is true then we consider data as signed
599     */
600    public static double getValue(short[] array, int offset, boolean signed)
601    {
602        return TypeUtil.toDouble(array[offset], signed);
603    }
604
605    /**
606     * Get value as double from specified int array and offset.<br>
607     * If signed is true then we consider data as signed
608     */
609    public static double getValue(int[] array, int offset, boolean signed)
610    {
611        return TypeUtil.toDouble(array[offset], signed);
612    }
613
614    /**
615     * Get value as double from specified long array and offset.<br>
616     * If signed is true then we consider data as signed
617     */
618    public static double getValue(long[] array, int offset, boolean signed)
619    {
620        return TypeUtil.toDouble(array[offset], signed);
621    }
622
623    /**
624     * Get value as double from specified float array and offset.
625     */
626    public static double getValue(float[] array, int offset)
627    {
628        return array[offset];
629    }
630
631    /**
632     * Get value as double from specified double array and offset.
633     */
634    public static double getValue(double[] array, int offset)
635    {
636        return array[offset];
637    }
638
639    //
640
641    /**
642     * Get value as float from specified byte array and offset.<br>
643     * If signed is true then we consider data as signed
644     */
645    public static float getValueAsFloat(byte[] array, int offset, boolean signed)
646    {
647        return TypeUtil.toFloat(array[offset], signed);
648    }
649
650    /**
651     * Get value as float from specified short array and offset.<br>
652     * If signed is true then we consider data as signed
653     */
654    public static float getValueAsFloat(short[] array, int offset, boolean signed)
655    {
656        return TypeUtil.toFloat(array[offset], signed);
657    }
658
659    /**
660     * Get value as float from specified int array and offset.<br>
661     * If signed is true then we consider data as signed
662     */
663    public static float getValueAsFloat(int[] array, int offset, boolean signed)
664    {
665        return TypeUtil.toFloat(array[offset], signed);
666    }
667
668    /**
669     * Get value as float from specified long array and offset.<br>
670     * If signed is true then we consider data as signed
671     */
672    public static float getValueAsFloat(long[] array, int offset, boolean signed)
673    {
674        return TypeUtil.toFloat(array[offset], signed);
675    }
676
677    /**
678     * Get value as float from specified float array and offset.
679     */
680    public static float getValueAsFloat(float[] array, int offset)
681    {
682        return array[offset];
683    }
684
685    /**
686     * Get value as float from specified double array and offset.
687     */
688    public static float getValueAsFloat(double[] array, int offset)
689    {
690        return (float) array[offset];
691    }
692
693    //
694
695    /**
696     * Get value as int from specified byte array and offset.<br>
697     * If signed is true then we consider data as signed
698     */
699    public static int getValueAsInt(byte[] array, int offset, boolean signed)
700    {
701        return TypeUtil.toInt(array[offset], signed);
702    }
703
704    /**
705     * Get value as int from specified short array and offset.<br>
706     * If signed is true then we consider data as signed
707     */
708    public static int getValueAsInt(short[] array, int offset, boolean signed)
709    {
710        return TypeUtil.toInt(array[offset], signed);
711    }
712
713    /**
714     * Get value as int from specified int array and offset.<br>
715     */
716    public static int getValueAsInt(int[] array, int offset)
717    {
718        // can't unsign here
719        return array[offset];
720    }
721
722    /**
723     * Get value as int from specified long array and offset.<br>
724     */
725    public static int getValueAsInt(long[] array, int offset)
726    {
727        return (int) array[offset];
728    }
729
730    /**
731     * Get value as int from specified float array and offset.
732     */
733    public static int getValueAsInt(float[] array, int offset)
734    {
735        return (int) array[offset];
736    }
737
738    /**
739     * Get value as int from specified double array and offset.
740     */
741    public static int getValueAsInt(double[] array, int offset)
742    {
743        return (int) array[offset];
744    }
745
746    //
747
748    /**
749     * Get value as int from specified byte array and offset.<br>
750     * If signed is true then we consider data as signed
751     */
752    public static long getValueAsLong(byte[] array, int offset, boolean signed)
753    {
754        return TypeUtil.toLong(array[offset], signed);
755    }
756
757    /**
758     * Get value as int from specified short array and offset.<br>
759     * If signed is true then we consider data as signed
760     */
761    public static long getValueAsLong(short[] array, int offset, boolean signed)
762    {
763        return TypeUtil.toLong(array[offset], signed);
764
765    }
766
767    /**
768     * Get value as int from specified int array and offset.<br>
769     */
770    public static long getValueAsLong(int[] array, int offset, boolean signed)
771    {
772        return TypeUtil.toLong(array[offset], signed);
773
774    }
775
776    /**
777     * Get value as int from specified long array and offset.<br>
778     */
779    public static long getValueAsLong(long[] array, int offset)
780    {
781        // can't unsign here
782        return array[offset];
783    }
784
785    /**
786     * Get value as int from specified float array and offset.
787     */
788    public static long getValueAsLong(float[] array, int offset)
789    {
790        return (long) array[offset];
791    }
792
793    /**
794     * Get value as int from specified double array and offset.
795     */
796    public static long getValueAsLong(double[] array, int offset)
797    {
798        return (long) array[offset];
799    }
800
801    /**
802     * Set value at specified offset as double value.
803     */
804    public static void setValue(byte[] array, int offset, double value)
805    {
806        array[offset] = (byte) value;
807    }
808
809    /**
810     * Set value at specified offset as double value.
811     */
812    public static void setValue(short[] array, int offset, double value)
813    {
814        array[offset] = (short) value;
815    }
816
817    /**
818     * Set value at specified offset as double value.
819     */
820    public static void setValue(int[] array, int offset, double value)
821    {
822        array[offset] = (int) value;
823    }
824
825    /**
826     * Set value at specified offset as double value.
827     */
828    public static void setValue(long[] array, int offset, double value)
829    {
830        array[offset] = (long) value;
831    }
832
833    /**
834     * Set value at specified offset as double value.
835     */
836    public static void setValue(float[] array, int offset, double value)
837    {
838        array[offset] = (float) value;
839    }
840
841    /**
842     * Set value at specified offset as double value.
843     */
844    public static void setValue(double[] array, int offset, double value)
845    {
846        array[offset] = value;
847    }
848
849    /**
850     * Return true is the specified arrays are equals
851     */
852    public static boolean arrayByteCompare(byte[] array1, byte[] array2)
853    {
854        return Arrays.equals(array1, array2);
855    }
856
857    /**
858     * Return true is the specified arrays are equals
859     */
860    public static boolean arrayShortCompare(short[] array1, short[] array2)
861    {
862        return Arrays.equals(array1, array2);
863    }
864
865    /**
866     * Return true is the specified arrays are equals
867     */
868    public static boolean arrayIntCompare(int[] array1, int[] array2)
869    {
870        return Arrays.equals(array1, array2);
871    }
872
873    /**
874     * Return true is the specified arrays are equals
875     */
876    public static boolean arrayLongCompare(long[] array1, long[] array2)
877    {
878        return Arrays.equals(array1, array2);
879    }
880
881    /**
882     * Return true is the specified arrays are equals
883     */
884    public static boolean arrayFloatCompare(float[] array1, float[] array2)
885    {
886        return Arrays.equals(array1, array2);
887    }
888
889    /**
890     * Return true is the specified arrays are equals
891     */
892    public static boolean arrayDoubleCompare(double[] array1, double[] array2)
893    {
894        return Arrays.equals(array1, array2);
895    }
896
897    //
898    //
899    //
900
901    /**
902     * Copy a region of data from <code>src</code> to <code>dst</code>.<br>
903     * Both array are 1D but represents 2D data as we have in an image plane.
904     * 
905     * @param src
906     *        source data array (should be same type than destination data array)
907     * @param srcDim
908     *        source rectangular data dimension (array length should be >= (Dimension.width * Dimension.heigth))
909     * @param srcRegion
910     *        source rectangular region to copy (assume the whole data based on srcDim if null)
911     * @param dst
912     *        destination data array (should be same type than source data array)
913     * @param dstDim
914     *        destination rectangular data dimension (array length should be >= (Dimension.width * Dimension.heigth))
915     * @param dstPt
916     *        destination X,Y position (assume [0,0] if null)
917     * @param signed
918     *        if the source data array should be considered as signed data (meaningful for integer data type only)
919     */
920    public static void copyRect(Object src, Dimension srcDim, Rectangle srcRegion, Object dst, Dimension dstDim,
921            Point dstPt, boolean signed)
922    {
923        if ((src == null) || (srcDim == null) || (dst == null) || (dstDim == null))
924            return;
925
926        // source image region
927        Rectangle adjSrcRegion = (srcRegion != null) ? srcRegion : new Rectangle(srcDim);
928
929        // negative destination x position ?
930        if ((dstPt != null) && (dstPt.x < 0))
931        {
932            // adjust source rect and width
933            adjSrcRegion.x += -dstPt.x;
934            adjSrcRegion.width -= -dstPt.x;
935        }
936        // negative destination y position ?
937        if ((dstPt != null) && (dstPt.y < 0))
938        {
939            // adjust source rect and height
940            adjSrcRegion.y += -dstPt.y;
941            adjSrcRegion.height -= -dstPt.y;
942        }
943
944        // limit to source image size
945        adjSrcRegion = adjSrcRegion.intersection(new Rectangle(srcDim));
946
947        // destination image region
948        Rectangle adjDstRegion = new Rectangle((dstPt != null) ? dstPt : new Point(), adjSrcRegion.getSize());
949        // limit to destination image size
950        adjDstRegion = adjDstRegion.intersection(new Rectangle(dstDim));
951
952        final int w = Math.min(adjSrcRegion.width, adjDstRegion.width);
953        final int h = Math.min(adjSrcRegion.height, adjDstRegion.height);
954
955        // nothing to copy
956        if ((w <= 0) || (h <= 0))
957            return;
958
959        final int srcSizeX = srcDim.width;
960        final int dstSizeX = dstDim.width;
961
962        int srcOffset = adjSrcRegion.x + (adjSrcRegion.y * srcSizeX);
963        int dstOffset = adjDstRegion.x + (adjDstRegion.y * dstSizeX);
964
965        for (int y = 0; y < h; y++)
966        {
967            // do data copy (and conversion if needed)
968            Array1DUtil.arrayToArray(src, srcOffset, dst, dstOffset, w, signed);
969            srcOffset += srcSizeX;
970            dstOffset += dstSizeX;
971        }
972    }
973
974    /**
975     * Same as Arrays.fill() but applied to Object array from a double value
976     */
977    public static void fill(Object array, double value)
978    {
979        fill(array, 0, ArrayUtil.getLength(array), value);
980    }
981
982    /**
983     * Same as Arrays.fill() but applied to Object array from a double value
984     */
985    public static void fill(Object array, int from, int to, double value)
986    {
987        switch (ArrayUtil.getDataType(array))
988        {
989            case BYTE:
990                fill((byte[]) array, from, to, (byte) value);
991                break;
992
993            case SHORT:
994                fill((short[]) array, from, to, (short) value);
995                break;
996
997            case INT:
998                fill((int[]) array, from, to, (int) value);
999                break;
1000
1001            case LONG:
1002                fill((long[]) array, from, to, (long) value);
1003                break;
1004
1005            case FLOAT:
1006                fill((float[]) array, from, to, (float) value);
1007                break;
1008
1009            case DOUBLE:
1010                fill((double[]) array, from, to, value);
1011                break;
1012        }
1013    }
1014
1015    /**
1016     * Same as {@link Arrays#fill(byte[], int, int, byte)}
1017     */
1018    public static void fill(byte[] array, int from, int to, byte value)
1019    {
1020        for (int i = from; i < to; i++)
1021            array[i] = value;
1022    }
1023
1024    /**
1025     * Same as {@link Arrays#fill(short[], int, int, short)}
1026     */
1027    public static void fill(short[] array, int from, int to, short value)
1028    {
1029        for (int i = from; i < to; i++)
1030            array[i] = value;
1031    }
1032
1033    /**
1034     * Same as {@link Arrays#fill(int[], int, int, int)}
1035     */
1036    public static void fill(int[] array, int from, int to, int value)
1037    {
1038        for (int i = from; i < to; i++)
1039            array[i] = value;
1040    }
1041
1042    /**
1043     * Same as {@link Arrays#fill(long[], int, int, long)}
1044     */
1045    public static void fill(long[] array, int from, int to, long value)
1046    {
1047        for (int i = from; i < to; i++)
1048            array[i] = value;
1049    }
1050
1051    /**
1052     * Same as {@link Arrays#fill(float[], int, int, float)}
1053     */
1054    public static void fill(float[] array, int from, int to, float value)
1055    {
1056        for (int i = from; i < to; i++)
1057            array[i] = value;
1058    }
1059
1060    /**
1061     * Same as {@link Arrays#fill(double[], int, int, double)}
1062     */
1063    public static void fill(double[] array, int from, int to, double value)
1064    {
1065        for (int i = from; i < to; i++)
1066            array[i] = value;
1067    }
1068
1069    /**
1070     * Copy 'cnt' elements from 'from' index to 'to' index in a safe manner.<br>
1071     * i.e: without overriding any data
1072     */
1073    public static void innerCopy(Object array, int from, int to, int cnt)
1074    {
1075        if (array == null)
1076            return;
1077
1078        switch (ArrayUtil.getDataType(array))
1079        {
1080            case BYTE:
1081                Array1DUtil.innerCopy((byte[]) array, from, to, cnt);
1082                return;
1083
1084            case SHORT:
1085                Array1DUtil.innerCopy((short[]) array, from, to, cnt);
1086                return;
1087
1088            case INT:
1089                Array1DUtil.innerCopy((int[]) array, from, to, cnt);
1090                return;
1091
1092            case LONG:
1093                Array1DUtil.innerCopy((long[]) array, from, to, cnt);
1094                return;
1095
1096            case FLOAT:
1097                Array1DUtil.innerCopy((float[]) array, from, to, cnt);
1098                return;
1099
1100            case DOUBLE:
1101                Array1DUtil.innerCopy((double[]) array, from, to, cnt);
1102                return;
1103        }
1104
1105        // use generic code
1106        final int delta = to - from;
1107
1108        if (delta == 0)
1109            return;
1110
1111        final int length = Array.getLength(array);
1112
1113        if ((from < 0) || (to < 0) || (from >= length) || (to >= length))
1114            return;
1115
1116        final int adjCnt;
1117
1118        // forward copy
1119        if (delta < 0)
1120        {
1121            // adjust copy size
1122            if ((from + cnt) >= length)
1123                adjCnt = length - from;
1124            else
1125                adjCnt = cnt;
1126
1127            int to_ = to;
1128            int from_ = from;
1129            for (int i = 0; i < adjCnt; i++)
1130                Array.set(array, to_++, Array.get(array, from_++));
1131        }
1132        else
1133        // backward copy
1134        {
1135            // adjust copy size
1136            if ((to + cnt) >= length)
1137                adjCnt = length - to;
1138            else
1139                adjCnt = cnt;
1140
1141            int to_ = to + cnt;
1142            int from_ = from + cnt;
1143            for (int i = 0; i < adjCnt; i++)
1144                Array.set(array, --to_, Array.get(array, --from_));
1145        }
1146
1147    }
1148
1149    /**
1150     * Copy 'cnt' elements from 'from' index to 'to' index in a safe manner (no overlap)
1151     */
1152    public static void innerCopy(byte[] array, int from, int to, int cnt)
1153    {
1154        final int delta = to - from;
1155
1156        if ((array == null) || (delta == 0))
1157            return;
1158
1159        final int length = array.length;
1160
1161        if ((from < 0) || (to < 0) || (from >= length) || (to >= length))
1162            return;
1163
1164        final int adjCnt;
1165
1166        // forward copy
1167        if (delta < 0)
1168        {
1169            // adjust copy size
1170            if ((from + cnt) >= length)
1171                adjCnt = length - from;
1172            else
1173                adjCnt = cnt;
1174
1175            int to_ = to;
1176            int from_ = from;
1177            for (int i = 0; i < adjCnt; i++)
1178                array[to_++] = array[from_++];
1179        }
1180        else
1181        // backward copy
1182        {
1183            // adjust copy size
1184            if ((to + cnt) >= length)
1185                adjCnt = length - to;
1186            else
1187                adjCnt = cnt;
1188
1189            int to_ = to + cnt;
1190            int from_ = from + cnt;
1191            for (int i = 0; i < adjCnt; i++)
1192                array[--to_] = array[--from_];
1193        }
1194    }
1195
1196    /**
1197     * Copy 'cnt' elements from 'from' index to 'to' index in a safe manner (no overlap)
1198     */
1199    public static void innerCopy(short[] array, int from, int to, int cnt)
1200    {
1201        final int delta = to - from;
1202
1203        if ((array == null) || (delta == 0))
1204            return;
1205
1206        final int length = array.length;
1207
1208        if ((from < 0) || (to < 0) || (from >= length) || (to >= length))
1209            return;
1210
1211        final int adjCnt;
1212
1213        // forward copy
1214        if (delta < 0)
1215        {
1216            // adjust copy size
1217            if ((from + cnt) >= length)
1218                adjCnt = length - from;
1219            else
1220                adjCnt = cnt;
1221
1222            int to_ = to;
1223            int from_ = from;
1224            for (int i = 0; i < adjCnt; i++)
1225                array[to_++] = array[from_++];
1226        }
1227        else
1228        // backward copy
1229        {
1230            // adjust copy size
1231            if ((to + cnt) >= length)
1232                adjCnt = length - to;
1233            else
1234                adjCnt = cnt;
1235
1236            int to_ = to + cnt;
1237            int from_ = from + cnt;
1238            for (int i = 0; i < adjCnt; i++)
1239                array[--to_] = array[--from_];
1240        }
1241    }
1242
1243    /**
1244     * Copy 'cnt' elements from 'from' index to 'to' index in a safe manner (no overlap)
1245     */
1246    public static void innerCopy(int[] array, int from, int to, int cnt)
1247    {
1248        final int delta = to - from;
1249
1250        if ((array == null) || (delta == 0))
1251            return;
1252
1253        final int length = array.length;
1254
1255        if ((from < 0) || (to < 0) || (from >= length) || (to >= length))
1256            return;
1257
1258        final int adjCnt;
1259
1260        // forward copy
1261        if (delta < 0)
1262        {
1263            // adjust copy size
1264            if ((from + cnt) >= length)
1265                adjCnt = length - from;
1266            else
1267                adjCnt = cnt;
1268
1269            int to_ = to;
1270            int from_ = from;
1271            for (int i = 0; i < adjCnt; i++)
1272                array[to_++] = array[from_++];
1273        }
1274        else
1275        // backward copy
1276        {
1277            // adjust copy size
1278            if ((to + cnt) >= length)
1279                adjCnt = length - to;
1280            else
1281                adjCnt = cnt;
1282
1283            int to_ = to + cnt;
1284            int from_ = from + cnt;
1285            for (int i = 0; i < adjCnt; i++)
1286                array[--to_] = array[--from_];
1287        }
1288    }
1289
1290    /**
1291     * Copy 'cnt' elements from 'from' index to 'to' index in a safe manner (no overlap)
1292     */
1293    public static void innerCopy(long[] array, int from, int to, int cnt)
1294    {
1295        final int delta = to - from;
1296
1297        if ((array == null) || (delta == 0))
1298            return;
1299
1300        final int length = array.length;
1301
1302        if ((from < 0) || (to < 0) || (from >= length) || (to >= length))
1303            return;
1304
1305        final int adjCnt;
1306
1307        // forward copy
1308        if (delta < 0)
1309        {
1310            // adjust copy size
1311            if ((from + cnt) >= length)
1312                adjCnt = length - from;
1313            else
1314                adjCnt = cnt;
1315
1316            int to_ = to;
1317            int from_ = from;
1318            for (int i = 0; i < adjCnt; i++)
1319                array[to_++] = array[from_++];
1320        }
1321        else
1322        // backward copy
1323        {
1324            // adjust copy size
1325            if ((to + cnt) >= length)
1326                adjCnt = length - to;
1327            else
1328                adjCnt = cnt;
1329
1330            int to_ = to + cnt;
1331            int from_ = from + cnt;
1332            for (int i = 0; i < adjCnt; i++)
1333                array[--to_] = array[--from_];
1334        }
1335    }
1336
1337    /**
1338     * Copy 'cnt' elements from 'from' index to 'to' index in a safe manner (no overlap)
1339     */
1340    public static void innerCopy(float[] array, int from, int to, int cnt)
1341    {
1342        final int delta = to - from;
1343
1344        if ((array == null) || (delta == 0))
1345            return;
1346
1347        final int length = array.length;
1348
1349        if ((from < 0) || (to < 0) || (from >= length) || (to >= length))
1350            return;
1351
1352        final int adjCnt;
1353
1354        // forward copy
1355        if (delta < 0)
1356        {
1357            // adjust copy size
1358            if ((from + cnt) >= length)
1359                adjCnt = length - from;
1360            else
1361                adjCnt = cnt;
1362
1363            int to_ = to;
1364            int from_ = from;
1365            for (int i = 0; i < adjCnt; i++)
1366                array[to_++] = array[from_++];
1367        }
1368        else
1369        // backward copy
1370        {
1371            // adjust copy size
1372            if ((to + cnt) >= length)
1373                adjCnt = length - to;
1374            else
1375                adjCnt = cnt;
1376
1377            int to_ = to + cnt;
1378            int from_ = from + cnt;
1379            for (int i = 0; i < adjCnt; i++)
1380                array[--to_] = array[--from_];
1381        }
1382    }
1383
1384    /**
1385     * Copy 'cnt' elements from 'from' index to 'to' index in a safe manner (no overlap)
1386     */
1387    public static void innerCopy(double[] array, int from, int to, int cnt)
1388    {
1389        final int delta = to - from;
1390
1391        if ((array == null) || (delta == 0))
1392            return;
1393
1394        final int length = array.length;
1395
1396        if ((from < 0) || (to < 0) || (from >= length) || (to >= length))
1397            return;
1398
1399        final int adjCnt;
1400
1401        // forward copy
1402        if (delta < 0)
1403        {
1404            // adjust copy size
1405            if ((from + cnt) >= length)
1406                adjCnt = length - from;
1407            else
1408                adjCnt = cnt;
1409
1410            int to_ = to;
1411            int from_ = from;
1412            for (int i = 0; i < adjCnt; i++)
1413                array[to_++] = array[from_++];
1414        }
1415        else
1416        // backward copy
1417        {
1418            // adjust copy size
1419            if ((to + cnt) >= length)
1420                adjCnt = length - to;
1421            else
1422                adjCnt = cnt;
1423
1424            int to_ = to + cnt;
1425            int from_ = from + cnt;
1426            for (int i = 0; i < adjCnt; i++)
1427                array[--to_] = array[--from_];
1428        }
1429    }
1430
1431    /**
1432     * Return the 'in' array as a single dimension array.<br>
1433     * The resulting array is returned in 'out' at specified offset.<br>
1434     * If (out == null) a new array is allocated.
1435     */
1436    public static byte[] toByteArray1D(byte[] in, byte[] out, int offset)
1437    {
1438        final int len = getTotalLength(in);
1439        final byte[] result = allocIfNull(out, offset + len);
1440
1441        if (in != null)
1442            System.arraycopy(in, 0, result, offset, len);
1443
1444        return result;
1445    }
1446
1447    /**
1448     * Return the 'in' array as a single dimension array.<br>
1449     * The resulting array is returned in 'out' at specified offset.<br>
1450     * If (out == null) a new array is allocated.
1451     */
1452    public static short[] toShortArray1D(short[] in, short[] out, int offset)
1453    {
1454        final int len = getTotalLength(in);
1455        final short[] result = allocIfNull(out, offset + len);
1456
1457        if (in != null)
1458            System.arraycopy(in, 0, result, offset, len);
1459
1460        return result;
1461    }
1462
1463    /**
1464     * Return the 'in' array as a single dimension array.<br>
1465     * The resulting array is returned in 'out' at specified offset.<br>
1466     * If (out == null) a new array is allocated.
1467     */
1468    public static int[] toIntArray1D(int[] in, int[] out, int offset)
1469    {
1470        final int len = getTotalLength(in);
1471        final int[] result = allocIfNull(out, offset + len);
1472
1473        if (in != null)
1474            System.arraycopy(in, 0, result, offset, len);
1475
1476        return result;
1477    }
1478
1479    /**
1480     * Return the 'in' array as a single dimension array.<br>
1481     * The resulting array is returned in 'out' at specified offset.<br>
1482     * If (out == null) a new array is allocated.
1483     */
1484    public static long[] toLongArray1D(long[] in, long[] out, int offset)
1485    {
1486        final int len = getTotalLength(in);
1487        final long[] result = allocIfNull(out, offset + len);
1488
1489        if (in != null)
1490            System.arraycopy(in, 0, result, offset, len);
1491
1492        return result;
1493    }
1494
1495    /**
1496     * Return the 'in' array as a single dimension array.<br>
1497     * The resulting array is returned in 'out' at specified offset.<br>
1498     * If (out == null) a new array is allocated.
1499     */
1500    public static float[] toFloatArray1D(float[] in, float[] out, int offset)
1501    {
1502        final int len = getTotalLength(in);
1503        final float[] result = allocIfNull(out, offset + len);
1504
1505        if (in != null)
1506            System.arraycopy(in, 0, result, offset, len);
1507
1508        return result;
1509    }
1510
1511    /**
1512     * Return the 'in' array as a single dimension array.<br>
1513     * The resulting array is returned in 'out' at specified offset.<br>
1514     * If (out == null) a new array is allocated.
1515     */
1516    public static double[] toDoubleArray1D(double[] in, double[] out, int offset)
1517    {
1518        final int len = getTotalLength(in);
1519        final double[] result = allocIfNull(out, offset + len);
1520
1521        if (in != null)
1522            System.arraycopy(in, 0, result, offset, len);
1523
1524        return result;
1525    }
1526
1527    /**
1528     * Convert and return the 'in' 1D array in 'out' 1D array type.<br>
1529     * 
1530     * @param in
1531     *        input array
1532     * @param inOffset
1533     *        position where we start read data from
1534     * @param out
1535     *        output array which is used to receive result (and so define wanted type)
1536     * @param outOffset
1537     *        position where we start to write data to
1538     * @param length
1539     *        number of value to convert (-1 means we will use the maximum possible length)
1540     * @param signed
1541     *        if input data are integer type then we assume them as signed data
1542     */
1543    public static Object arrayToArray(Object in, int inOffset, Object out, int outOffset, int length, boolean signed)
1544    {
1545        switch (ArrayUtil.getDataType(in))
1546        {
1547            case BYTE:
1548                return byteArrayToArray((byte[]) in, inOffset, out, outOffset, length, signed);
1549            case SHORT:
1550                return shortArrayToArray((short[]) in, inOffset, out, outOffset, length, signed);
1551            case INT:
1552                return intArrayToArray((int[]) in, inOffset, out, outOffset, length, signed);
1553            case LONG:
1554                return longArrayToArray((long[]) in, inOffset, out, outOffset, length, signed);
1555            case FLOAT:
1556                return floatArrayToArray((float[]) in, inOffset, out, outOffset, length);
1557            case DOUBLE:
1558                return doubleArrayToArray((double[]) in, inOffset, out, outOffset, length);
1559            default:
1560                return out;
1561        }
1562    }
1563
1564    /**
1565     * Convert and return the 'in' 1D array in 'out' 1D array type.
1566     * 
1567     * @param in
1568     *        input array
1569     * @param out
1570     *        output array which is used to receive result (and so define wanted type)
1571     * @param signed
1572     *        if input data are integer type then we assume them as signed data
1573     */
1574    public static Object arrayToArray(Object in, Object out, boolean signed)
1575    {
1576        return arrayToArray(in, 0, out, 0, -1, signed);
1577    }
1578
1579    /**
1580     * Convert and return the 'in' double array in 'out' array type.<br>
1581     * 
1582     * @param in
1583     *        input array
1584     * @param inOffset
1585     *        position where we start read data from
1586     * @param out
1587     *        output array which is used to receive result (and so define wanted type)
1588     * @param outOffset
1589     *        position where we start to write data to
1590     * @param length
1591     *        number of value to convert (-1 means we will use the maximum possible length)
1592     */
1593    public static Object doubleArrayToArray(double[] in, int inOffset, Object out, int outOffset, int length)
1594    {
1595        switch (ArrayUtil.getDataType(out))
1596        {
1597            case BYTE:
1598                return doubleArrayToByteArray(in, inOffset, (byte[]) out, outOffset, length);
1599            case SHORT:
1600                return doubleArrayToShortArray(in, inOffset, (short[]) out, outOffset, length);
1601            case INT:
1602                return doubleArrayToIntArray(in, inOffset, (int[]) out, outOffset, length);
1603            case LONG:
1604                return doubleArrayToLongArray(in, inOffset, (long[]) out, outOffset, length);
1605            case FLOAT:
1606                return doubleArrayToFloatArray(in, inOffset, (float[]) out, outOffset, length);
1607            case DOUBLE:
1608                return doubleArrayToDoubleArray(in, inOffset, (double[]) out, outOffset, length);
1609            default:
1610                return out;
1611        }
1612    }
1613
1614    /**
1615     * Convert and return the 'in' double array in 'out' array type.<br>
1616     * 
1617     * @param in
1618     *        input array
1619     * @param out
1620     *        output array which is used to receive result (and so define wanted type)
1621     */
1622    public static Object doubleArrayToArray(double[] in, Object out)
1623    {
1624        return doubleArrayToArray(in, 0, out, 0, -1);
1625    }
1626
1627    /**
1628     * Convert and return the 'in' float array in 'out' array type.<br>
1629     * 
1630     * @param in
1631     *        input array
1632     * @param inOffset
1633     *        position where we start read data from
1634     * @param out
1635     *        output array which is used to receive result (and so define wanted type)
1636     * @param outOffset
1637     *        position where we start to write data to
1638     * @param length
1639     *        number of value to convert (-1 means we will use the maximum possible length)
1640     */
1641    public static Object floatArrayToArray(float[] in, int inOffset, Object out, int outOffset, int length)
1642    {
1643        switch (ArrayUtil.getDataType(out))
1644        {
1645            case BYTE:
1646                return floatArrayToByteArray(in, inOffset, (byte[]) out, outOffset, length);
1647            case SHORT:
1648                return floatArrayToShortArray(in, inOffset, (short[]) out, outOffset, length);
1649            case INT:
1650                return floatArrayToIntArray(in, inOffset, (int[]) out, outOffset, length);
1651            case LONG:
1652                return floatArrayToLongArray(in, inOffset, (long[]) out, outOffset, length);
1653            case FLOAT:
1654                return floatArrayToFloatArray(in, inOffset, (float[]) out, outOffset, length);
1655            case DOUBLE:
1656                return floatArrayToDoubleArray(in, inOffset, (double[]) out, outOffset, length);
1657            default:
1658                return out;
1659        }
1660    }
1661
1662    /**
1663     * Convert and return the 'in' float array in 'out' array type.<br>
1664     * 
1665     * @param in
1666     *        input array
1667     * @param out
1668     *        output array which is used to receive result (and so define wanted type)
1669     */
1670    public static Object floatArrayToArray(float[] in, Object out)
1671    {
1672        return floatArrayToArray(in, 0, out, 0, -1);
1673    }
1674
1675    /**
1676     * Convert and return the 'in' long array in 'out' array type.<br>
1677     * 
1678     * @param in
1679     *        input array
1680     * @param inOffset
1681     *        position where we start read data from
1682     * @param out
1683     *        output array which is used to receive result (and so define wanted type)
1684     * @param outOffset
1685     *        position where we start to write data to
1686     * @param length
1687     *        number of value to convert (-1 means we will use the maximum possible length)
1688     * @param signed
1689     *        assume input data as signed data
1690     */
1691    public static Object longArrayToArray(long[] in, int inOffset, Object out, int outOffset, int length,
1692            boolean signed)
1693    {
1694        switch (ArrayUtil.getDataType(out))
1695        {
1696            case BYTE:
1697                return longArrayToByteArray(in, inOffset, (byte[]) out, outOffset, length);
1698            case SHORT:
1699                return longArrayToShortArray(in, inOffset, (short[]) out, outOffset, length);
1700            case INT:
1701                return longArrayToIntArray(in, inOffset, (int[]) out, outOffset, length);
1702            case LONG:
1703                return longArrayToLongArray(in, inOffset, (long[]) out, outOffset, length);
1704            case FLOAT:
1705                return longArrayToFloatArray(in, inOffset, (float[]) out, outOffset, length, signed);
1706            case DOUBLE:
1707                return longArrayToDoubleArray(in, inOffset, (double[]) out, outOffset, length, signed);
1708            default:
1709                return out;
1710        }
1711    }
1712
1713    /**
1714     * Convert and return the 'in' long array in 'out' array type.<br>
1715     * 
1716     * @param in
1717     *        input array
1718     * @param out
1719     *        output array which is used to receive result (and so define wanted type)
1720     * @param signed
1721     *        assume input data as signed data
1722     */
1723    public static Object longArrayToArray(long[] in, Object out, boolean signed)
1724    {
1725        return longArrayToArray(in, 0, out, 0, -1, signed);
1726    }
1727
1728    /**
1729     * Convert and return the 'in' integer array in 'out' array type.<br>
1730     * 
1731     * @param in
1732     *        input array
1733     * @param inOffset
1734     *        position where we start read data from
1735     * @param out
1736     *        output array which is used to receive result (and so define wanted type)
1737     * @param outOffset
1738     *        position where we start to write data to
1739     * @param length
1740     *        number of value to convert (-1 means we will use the maximum possible length)
1741     * @param signed
1742     *        assume input data as signed data
1743     */
1744    public static Object intArrayToArray(int[] in, int inOffset, Object out, int outOffset, int length, boolean signed)
1745    {
1746        switch (ArrayUtil.getDataType(out))
1747        {
1748            case BYTE:
1749                return intArrayToByteArray(in, inOffset, (byte[]) out, outOffset, length);
1750            case SHORT:
1751                return intArrayToShortArray(in, inOffset, (short[]) out, outOffset, length);
1752            case INT:
1753                return intArrayToIntArray(in, inOffset, (int[]) out, outOffset, length);
1754            case LONG:
1755                return intArrayToLongArray(in, inOffset, (long[]) out, outOffset, length, signed);
1756            case FLOAT:
1757                return intArrayToFloatArray(in, inOffset, (float[]) out, outOffset, length, signed);
1758            case DOUBLE:
1759                return intArrayToDoubleArray(in, inOffset, (double[]) out, outOffset, length, signed);
1760            default:
1761                return out;
1762        }
1763    }
1764
1765    /**
1766     * Convert and return the 'in' integer array in 'out' array type.<br>
1767     * 
1768     * @param in
1769     *        input array
1770     * @param out
1771     *        output array which is used to receive result (and so define wanted type)
1772     * @param signed
1773     *        assume input data as signed data
1774     */
1775    public static Object intArrayToArray(int[] in, Object out, boolean signed)
1776    {
1777        return intArrayToArray(in, 0, out, 0, -1, signed);
1778    }
1779
1780    /**
1781     * Convert and return the 'in' short array in 'out' array type.<br>
1782     * 
1783     * @param in
1784     *        input array
1785     * @param inOffset
1786     *        position where we start read data from
1787     * @param out
1788     *        output array which is used to receive result (and so define wanted type)
1789     * @param outOffset
1790     *        position where we start to write data to
1791     * @param length
1792     *        number of value to convert (-1 means we will use the maximum possible length)
1793     * @param signed
1794     *        assume input data as signed data
1795     */
1796    public static Object shortArrayToArray(short[] in, int inOffset, Object out, int outOffset, int length,
1797            boolean signed)
1798    {
1799        switch (ArrayUtil.getDataType(out))
1800        {
1801            case BYTE:
1802                return shortArrayToByteArray(in, inOffset, (byte[]) out, outOffset, length);
1803            case SHORT:
1804                return shortArrayToShortArray(in, inOffset, (short[]) out, outOffset, length);
1805            case INT:
1806                return shortArrayToIntArray(in, inOffset, (int[]) out, outOffset, length, signed);
1807            case LONG:
1808                return shortArrayToLongArray(in, inOffset, (long[]) out, outOffset, length, signed);
1809            case FLOAT:
1810                return shortArrayToFloatArray(in, inOffset, (float[]) out, outOffset, length, signed);
1811            case DOUBLE:
1812                return shortArrayToDoubleArray(in, inOffset, (double[]) out, outOffset, length, signed);
1813            default:
1814                return out;
1815        }
1816    }
1817
1818    /**
1819     * Convert and return the 'in' short array in 'out' array type.<br>
1820     * 
1821     * @param in
1822     *        input array
1823     * @param out
1824     *        output array which is used to receive result (and so define wanted type)
1825     * @param signed
1826     *        assume input data as signed data
1827     */
1828    public static Object shortArrayToArray(short[] in, Object out, boolean signed)
1829    {
1830        return shortArrayToArray(in, 0, out, 0, -1, signed);
1831    }
1832
1833    /**
1834     * Convert and return the 'in' byte array in 'out' array type.<br>
1835     * 
1836     * @param in
1837     *        input array
1838     * @param inOffset
1839     *        position where we start read data from
1840     * @param out
1841     *        output array which is used to receive result (and so define wanted type)
1842     * @param outOffset
1843     *        position where we start to write data to
1844     * @param length
1845     *        number of value to convert (-1 means we will use the maximum possible length)
1846     * @param signed
1847     *        assume input data as signed data
1848     */
1849    public static Object byteArrayToArray(byte[] in, int inOffset, Object out, int outOffset, int length,
1850            boolean signed)
1851    {
1852        switch (ArrayUtil.getDataType(out))
1853        {
1854            case BYTE:
1855                return byteArrayToByteArray(in, inOffset, (byte[]) out, outOffset, length);
1856            case SHORT:
1857                return byteArrayToShortArray(in, inOffset, (short[]) out, outOffset, length, signed);
1858            case INT:
1859                return byteArrayToIntArray(in, inOffset, (int[]) out, outOffset, length, signed);
1860            case LONG:
1861                return byteArrayToLongArray(in, inOffset, (long[]) out, outOffset, length, signed);
1862            case FLOAT:
1863                return byteArrayToFloatArray(in, inOffset, (float[]) out, outOffset, length, signed);
1864            case DOUBLE:
1865                return byteArrayToDoubleArray(in, inOffset, (double[]) out, outOffset, length, signed);
1866            default:
1867                return out;
1868        }
1869    }
1870
1871    /**
1872     * Convert and return the 'in' byte array in 'out' array type.<br>
1873     * 
1874     * @param in
1875     *        input array
1876     * @param out
1877     *        output array which is used to receive result (and so define wanted type)
1878     * @param signed
1879     *        assume input data as signed data
1880     */
1881    public static Object byteArrayToArray(byte[] in, Object out, boolean signed)
1882    {
1883        return byteArrayToArray(in, 0, out, 0, -1, signed);
1884    }
1885
1886    /**
1887     * Convert and return the 'in' array in 'out' double array.<br>
1888     * 
1889     * @param in
1890     *        input array
1891     * @param inOffset
1892     *        position where we start read data from
1893     * @param out
1894     *        output array which is used to receive result (and so define wanted type)
1895     * @param outOffset
1896     *        position where we start to write data to
1897     * @param length
1898     *        number of value to convert (-1 means we will use the maximum possible length)
1899     * @param signed
1900     *        assume input data as signed data
1901     */
1902    public static double[] arrayToDoubleArray(Object in, int inOffset, double[] out, int outOffset, int length,
1903            boolean signed)
1904    {
1905        switch (ArrayUtil.getDataType(in))
1906        {
1907            case BYTE:
1908                return byteArrayToDoubleArray((byte[]) in, inOffset, out, outOffset, length, signed);
1909            case SHORT:
1910                return shortArrayToDoubleArray((short[]) in, inOffset, out, outOffset, length, signed);
1911            case INT:
1912                return intArrayToDoubleArray((int[]) in, inOffset, out, outOffset, length, signed);
1913            case LONG:
1914                return longArrayToDoubleArray((long[]) in, inOffset, out, outOffset, length, signed);
1915            case FLOAT:
1916                return floatArrayToDoubleArray((float[]) in, inOffset, out, outOffset, length);
1917            case DOUBLE:
1918                return doubleArrayToDoubleArray((double[]) in, inOffset, out, outOffset, length);
1919            default:
1920                return out;
1921        }
1922    }
1923
1924    /**
1925     * Convert and return the 'in' array in 'out' double array.<br>
1926     * 
1927     * @param in
1928     *        input array
1929     * @param out
1930     *        output array which is used to receive result (and so define wanted type)
1931     * @param signed
1932     *        assume input data as signed data
1933     */
1934    public static double[] arrayToDoubleArray(Object in, double[] out, boolean signed)
1935    {
1936        return arrayToDoubleArray(in, 0, out, 0, -1, signed);
1937    }
1938
1939    /**
1940     * Convert and return the 'in' array as a double array.<br>
1941     * 
1942     * @param in
1943     *        input array
1944     * @param signed
1945     *        assume input data as signed data
1946     */
1947    public static double[] arrayToDoubleArray(Object in, boolean signed)
1948    {
1949        return arrayToDoubleArray(in, 0, null, 0, -1, signed);
1950    }
1951
1952    /**
1953     * Convert and return the 'in' array in 'out' float array.<br>
1954     * 
1955     * @param in
1956     *        input array
1957     * @param inOffset
1958     *        position where we start read data from
1959     * @param out
1960     *        output array which is used to receive result (and so define wanted type)
1961     * @param outOffset
1962     *        position where we start to write data to
1963     * @param length
1964     *        number of value to convert (-1 means we will use the maximum possible length)
1965     * @param signed
1966     *        assume input data as signed data
1967     */
1968    public static float[] arrayToFloatArray(Object in, int inOffset, float[] out, int outOffset, int length,
1969            boolean signed)
1970    {
1971        switch (ArrayUtil.getDataType(in))
1972        {
1973            case BYTE:
1974                return byteArrayToFloatArray((byte[]) in, inOffset, out, outOffset, length, signed);
1975            case SHORT:
1976                return shortArrayToFloatArray((short[]) in, inOffset, out, outOffset, length, signed);
1977            case INT:
1978                return intArrayToFloatArray((int[]) in, inOffset, out, outOffset, length, signed);
1979            case LONG:
1980                return longArrayToFloatArray((long[]) in, inOffset, out, outOffset, length, signed);
1981            case FLOAT:
1982                return floatArrayToFloatArray((float[]) in, inOffset, out, outOffset, length);
1983            case DOUBLE:
1984                return doubleArrayToFloatArray((double[]) in, inOffset, out, outOffset, length);
1985            default:
1986                return out;
1987        }
1988    }
1989
1990    /**
1991     * Convert and return the 'in' array in 'out' float array.<br>
1992     * 
1993     * @param in
1994     *        input array
1995     * @param out
1996     *        output array which is used to receive result (and so define wanted type)
1997     * @param signed
1998     *        assume input data as signed data
1999     */
2000    public static float[] arrayToFloatArray(Object in, float[] out, boolean signed)
2001    {
2002        return arrayToFloatArray(in, 0, out, 0, -1, signed);
2003    }
2004
2005    /**
2006     * Convert and return the 'in' array as a float array.<br>
2007     * 
2008     * @param in
2009     *        input array
2010     * @param signed
2011     *        assume input data as signed data
2012     */
2013    public static float[] arrayToFloatArray(Object in, boolean signed)
2014    {
2015        return arrayToFloatArray(in, 0, null, 0, -1, signed);
2016    }
2017
2018    /**
2019     * Convert and return the 'in' array in 'out' int array.<br>
2020     * 
2021     * @param in
2022     *        input array
2023     * @param inOffset
2024     *        position where we start read data from
2025     * @param out
2026     *        output array which is used to receive result (and so define wanted type)
2027     * @param outOffset
2028     *        position where we start to write data to
2029     * @param length
2030     *        number of value to convert (-1 means we will use the maximum possible length)
2031     * @param signed
2032     *        assume input data as signed data
2033     */
2034    public static int[] arrayToIntArray(Object in, int inOffset, int[] out, int outOffset, int length, boolean signed)
2035    {
2036        switch (ArrayUtil.getDataType(in))
2037        {
2038            case BYTE:
2039                return byteArrayToIntArray((byte[]) in, inOffset, out, outOffset, length, signed);
2040            case SHORT:
2041                return shortArrayToIntArray((short[]) in, inOffset, out, outOffset, length, signed);
2042            case INT:
2043                return intArrayToIntArray((int[]) in, inOffset, out, outOffset, length);
2044            case LONG:
2045                return longArrayToIntArray((long[]) in, inOffset, out, outOffset, length);
2046            case FLOAT:
2047                return floatArrayToIntArray((float[]) in, inOffset, out, outOffset, length);
2048            case DOUBLE:
2049                return doubleArrayToIntArray((double[]) in, inOffset, out, outOffset, length);
2050            default:
2051                return out;
2052        }
2053    }
2054
2055    /**
2056     * Convert and return the 'in' array in 'out' int array.<br>
2057     * 
2058     * @param in
2059     *        input array
2060     * @param out
2061     *        output array which is used to receive result (and so define wanted type)
2062     * @param signed
2063     *        assume input data as signed data
2064     */
2065    public static int[] arrayToIntArray(Object in, int[] out, boolean signed)
2066    {
2067        return arrayToIntArray(in, 0, out, 0, -1, signed);
2068    }
2069
2070    /**
2071     * Convert and return the 'in' array as a int array.<br>
2072     * 
2073     * @param in
2074     *        input array
2075     * @param signed
2076     *        assume input data as signed data
2077     */
2078    public static int[] arrayToIntArray(Object in, boolean signed)
2079    {
2080        return arrayToIntArray(in, 0, null, 0, -1, signed);
2081    }
2082
2083    /**
2084     * Convert and return the 'in' array in 'out' short array.<br>
2085     * 
2086     * @param in
2087     *        input array
2088     * @param inOffset
2089     *        position where we start read data from
2090     * @param out
2091     *        output array which is used to receive result (and so define wanted type)
2092     * @param outOffset
2093     *        position where we start to write data to
2094     * @param length
2095     *        number of value to convert (-1 means we will use the maximum possible length)
2096     * @param signed
2097     *        assume input data as signed data
2098     */
2099    public static short[] arrayToShortArray(Object in, int inOffset, short[] out, int outOffset, int length,
2100            boolean signed)
2101    {
2102        switch (ArrayUtil.getDataType(in))
2103        {
2104            case BYTE:
2105                return byteArrayToShortArray((byte[]) in, inOffset, out, outOffset, length, signed);
2106            case SHORT:
2107                return shortArrayToShortArray((short[]) in, inOffset, out, outOffset, length);
2108            case INT:
2109                return intArrayToShortArray((int[]) in, inOffset, out, outOffset, length);
2110            case LONG:
2111                return longArrayToShortArray((long[]) in, inOffset, out, outOffset, length);
2112            case FLOAT:
2113                return floatArrayToShortArray((float[]) in, inOffset, out, outOffset, length);
2114            case DOUBLE:
2115                return doubleArrayToShortArray((double[]) in, inOffset, out, outOffset, length);
2116            default:
2117                return out;
2118        }
2119    }
2120
2121    /**
2122     * Convert and return the 'in' array in 'out' short array.<br>
2123     * 
2124     * @param in
2125     *        input array
2126     * @param out
2127     *        output array which is used to receive result (and so define wanted type)
2128     * @param signed
2129     *        assume input data as signed data
2130     */
2131    public static short[] arrayToShortArray(Object in, short[] out, boolean signed)
2132    {
2133        return arrayToShortArray(in, 0, out, 0, -1, signed);
2134    }
2135
2136    /**
2137     * Convert and return the 'in' array as a short array.<br>
2138     * 
2139     * @param in
2140     *        input array
2141     * @param signed
2142     *        assume input data as signed data
2143     */
2144    public static short[] arrayToShortArray(Object in, boolean signed)
2145    {
2146        return arrayToShortArray(in, 0, null, 0, -1, signed);
2147    }
2148
2149    /**
2150     * Convert and return the 'in' array in 'out' byte array.<br>
2151     * 
2152     * @param in
2153     *        input array
2154     * @param inOffset
2155     *        position where we start read data from
2156     * @param out
2157     *        output array which is used to receive result (and so define wanted type)
2158     * @param outOffset
2159     *        position where we start to write data to
2160     * @param length
2161     *        number of value to convert (-1 means we will use the maximum possible length)
2162     */
2163    public static byte[] arrayToByteArray(Object in, int inOffset, byte[] out, int outOffset, int length)
2164    {
2165        switch (ArrayUtil.getDataType(in))
2166        {
2167            case BYTE:
2168                return byteArrayToByteArray((byte[]) in, inOffset, out, outOffset, length);
2169            case SHORT:
2170                return shortArrayToByteArray((short[]) in, inOffset, out, outOffset, length);
2171            case INT:
2172                return intArrayToByteArray((int[]) in, inOffset, out, outOffset, length);
2173            case LONG:
2174                return longArrayToByteArray((long[]) in, inOffset, out, outOffset, length);
2175            case FLOAT:
2176                return floatArrayToByteArray((float[]) in, inOffset, out, outOffset, length);
2177            case DOUBLE:
2178                return doubleArrayToByteArray((double[]) in, inOffset, out, outOffset, length);
2179            default:
2180                return out;
2181        }
2182    }
2183
2184    /**
2185     * Convert and return the 'in' array in 'out' byte array.<br>
2186     * 
2187     * @param in
2188     *        input array
2189     * @param out
2190     *        output array which is used to receive result (and so define wanted type)
2191     */
2192    public static byte[] arrayToByteArray(Object in, byte[] out)
2193    {
2194        return arrayToByteArray(in, 0, out, 0, -1);
2195    }
2196
2197    /**
2198     * Convert and return the 'in' array as a byte array.<br>
2199     * 
2200     * @param in
2201     *        input array
2202     */
2203    public static byte[] arrayToByteArray(Object in)
2204    {
2205        return arrayToByteArray(in, 0, null, 0, -1);
2206    }
2207
2208    public static double[] doubleArrayToDoubleArray(double[] in, int inOffset, double[] out, int outOffset, int length)
2209    {
2210        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2211        final double[] result = allocIfNull(out, outOffset + len);
2212
2213        System.arraycopy(in, inOffset, result, outOffset, len);
2214
2215        return result;
2216    }
2217
2218    public static float[] doubleArrayToFloatArray(double[] in, int inOffset, float[] out, int outOffset, int length)
2219    {
2220        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2221        final float[] result = allocIfNull(out, outOffset + len);
2222
2223        for (int i = 0; i < len; i++)
2224            result[i + outOffset] = (float) in[i + inOffset];
2225
2226        return result;
2227    }
2228
2229    public static long[] doubleArrayToLongArray(double[] in, int inOffset, long[] out, int outOffset, int length)
2230    {
2231        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2232        final long[] result = allocIfNull(out, outOffset + len);
2233
2234        for (int i = 0; i < len; i++)
2235            result[i + outOffset] = TypeUtil.toLong(in[i + inOffset]);
2236
2237        return result;
2238    }
2239
2240    public static int[] doubleArrayToIntArray(double[] in, int inOffset, int[] out, int outOffset, int length)
2241    {
2242        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2243        final int[] result = allocIfNull(out, outOffset + len);
2244
2245        for (int i = 0; i < len; i++)
2246            result[i + outOffset] = TypeUtil.toInt(in[i + inOffset]);
2247
2248        return result;
2249    }
2250
2251    public static short[] doubleArrayToShortArray(double[] in, int inOffset, short[] out, int outOffset, int length)
2252    {
2253        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2254        final short[] result = allocIfNull(out, outOffset + len);
2255
2256        for (int i = 0; i < len; i++)
2257            result[i + outOffset] = (short) in[i + inOffset];
2258
2259        return result;
2260    }
2261
2262    public static byte[] doubleArrayToByteArray(double[] in, int inOffset, byte[] out, int outOffset, int length)
2263    {
2264        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2265        final byte[] result = allocIfNull(out, outOffset + len);
2266
2267        for (int i = 0; i < len; i++)
2268            result[i + outOffset] = (byte) in[i + inOffset];
2269
2270        return result;
2271    }
2272
2273    public static double[] floatArrayToDoubleArray(float[] in, int inOffset, double[] out, int outOffset, int length)
2274    {
2275        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2276        final double[] result = allocIfNull(out, outOffset + len);
2277
2278        for (int i = 0; i < len; i++)
2279            result[i + outOffset] = in[i + inOffset];
2280
2281        return result;
2282    }
2283
2284    public static float[] floatArrayToFloatArray(float[] in, int inOffset, float[] out, int outOffset, int length)
2285    {
2286        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2287        final float[] result = allocIfNull(out, outOffset + len);
2288
2289        System.arraycopy(in, inOffset, result, outOffset, len);
2290
2291        return result;
2292    }
2293
2294    public static long[] floatArrayToLongArray(float[] in, int inOffset, long[] out, int outOffset, int length)
2295    {
2296        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2297        final long[] result = allocIfNull(out, outOffset + len);
2298
2299        for (int i = 0; i < len; i++)
2300            result[i + outOffset] = TypeUtil.toLong(in[i + inOffset]);
2301
2302        return result;
2303    }
2304
2305    public static int[] floatArrayToIntArray(float[] in, int inOffset, int[] out, int outOffset, int length)
2306    {
2307        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2308        final int[] result = allocIfNull(out, outOffset + len);
2309
2310        for (int i = 0; i < len; i++)
2311            result[i + outOffset] = TypeUtil.toInt(in[i + inOffset]);
2312
2313        return result;
2314    }
2315
2316    public static short[] floatArrayToShortArray(float[] in, int inOffset, short[] out, int outOffset, int length)
2317    {
2318        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2319        final short[] result = allocIfNull(out, outOffset + len);
2320
2321        for (int i = 0; i < len; i++)
2322            result[i + outOffset] = (short) in[i + inOffset];
2323
2324        return result;
2325    }
2326
2327    public static byte[] floatArrayToByteArray(float[] in, int inOffset, byte[] out, int outOffset, int length)
2328    {
2329        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2330        final byte[] result = allocIfNull(out, outOffset + len);
2331
2332        for (int i = 0; i < len; i++)
2333            result[i + outOffset] = (byte) in[i + inOffset];
2334
2335        return result;
2336    }
2337
2338    public static double[] longArrayToDoubleArray(long[] in, int inOffset, double[] out, int outOffset, int length,
2339            boolean signed)
2340    {
2341        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2342        final double[] result = allocIfNull(out, outOffset + len);
2343
2344        if (signed)
2345        {
2346            for (int i = 0; i < len; i++)
2347                result[i + outOffset] = in[i + inOffset];
2348        }
2349        else
2350        {
2351            for (int i = 0; i < len; i++)
2352                result[i + outOffset] = TypeUtil.unsign(in[i + inOffset]);
2353        }
2354
2355        return result;
2356    }
2357
2358    public static float[] longArrayToFloatArray(long[] in, int inOffset, float[] out, int outOffset, int length,
2359            boolean signed)
2360    {
2361        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2362        final float[] result = allocIfNull(out, outOffset + len);
2363
2364        if (signed)
2365        {
2366            for (int i = 0; i < len; i++)
2367                result[i + outOffset] = in[i + inOffset];
2368        }
2369        else
2370        {
2371            for (int i = 0; i < len; i++)
2372                result[i + outOffset] = TypeUtil.unsignF(in[i + inOffset]);
2373        }
2374
2375        return result;
2376    }
2377
2378    public static long[] longArrayToLongArray(long[] in, int inOffset, long[] out, int outOffset, int length)
2379    {
2380        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2381        final long[] result = allocIfNull(out, outOffset + len);
2382
2383        System.arraycopy(in, inOffset, result, outOffset, len);
2384
2385        return result;
2386    }
2387
2388    public static int[] longArrayToIntArray(long[] in, int inOffset, int[] out, int outOffset, int length)
2389    {
2390        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2391        final int[] result = allocIfNull(out, outOffset + len);
2392
2393        for (int i = 0; i < len; i++)
2394            result[i + outOffset] = (int) in[i + inOffset];
2395
2396        return result;
2397    }
2398
2399    public static short[] longArrayToShortArray(long[] in, int inOffset, short[] out, int outOffset, int length)
2400    {
2401        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2402        final short[] result = allocIfNull(out, outOffset + len);
2403
2404        for (int i = 0; i < len; i++)
2405            result[i + outOffset] = (short) in[i + inOffset];
2406
2407        return result;
2408    }
2409
2410    public static byte[] longArrayToByteArray(long[] in, int inOffset, byte[] out, int outOffset, int length)
2411    {
2412        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2413        final byte[] result = allocIfNull(out, outOffset + len);
2414
2415        for (int i = 0; i < len; i++)
2416            result[i + outOffset] = (byte) in[i + inOffset];
2417
2418        return result;
2419    }
2420
2421    public static double[] intArrayToDoubleArray(int[] in, int inOffset, double[] out, int outOffset, int length,
2422            boolean signed)
2423    {
2424        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2425        final double[] result = allocIfNull(out, outOffset + len);
2426
2427        if (signed)
2428        {
2429            for (int i = 0; i < len; i++)
2430                result[i + outOffset] = in[i + inOffset];
2431        }
2432        else
2433        {
2434            for (int i = 0; i < len; i++)
2435                result[i + outOffset] = TypeUtil.unsign(in[i + inOffset]);
2436        }
2437
2438        return result;
2439    }
2440
2441    public static float[] intArrayToFloatArray(int[] in, int inOffset, float[] out, int outOffset, int length,
2442            boolean signed)
2443    {
2444        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2445        final float[] result = allocIfNull(out, outOffset + len);
2446
2447        if (signed)
2448        {
2449            for (int i = 0; i < len; i++)
2450                result[i + outOffset] = in[i + inOffset];
2451        }
2452        else
2453        {
2454            for (int i = 0; i < len; i++)
2455                result[i + outOffset] = TypeUtil.unsign(in[i + inOffset]);
2456        }
2457
2458        return result;
2459    }
2460
2461    public static long[] intArrayToLongArray(int[] in, int inOffset, long[] out, int outOffset, int length,
2462            boolean signed)
2463    {
2464        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2465        final long[] result = allocIfNull(out, outOffset + len);
2466
2467        if (signed)
2468        {
2469            for (int i = 0; i < len; i++)
2470                result[i + outOffset] = in[i + inOffset];
2471        }
2472        else
2473        {
2474            for (int i = 0; i < len; i++)
2475                result[i + outOffset] = TypeUtil.unsign(in[i + inOffset]);
2476        }
2477
2478        return result;
2479    }
2480
2481    public static int[] intArrayToIntArray(int[] in, int inOffset, int[] out, int outOffset, int length)
2482    {
2483        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2484        final int[] result = allocIfNull(out, outOffset + len);
2485
2486        System.arraycopy(in, inOffset, result, outOffset, len);
2487
2488        return result;
2489    }
2490
2491    public static short[] intArrayToShortArray(int[] in, int inOffset, short[] out, int outOffset, int length)
2492    {
2493        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2494        final short[] result = allocIfNull(out, outOffset + len);
2495
2496        for (int i = 0; i < len; i++)
2497            result[i + outOffset] = (short) in[i + inOffset];
2498
2499        return result;
2500    }
2501
2502    public static byte[] intArrayToByteArray(int[] in, int inOffset, byte[] out, int outOffset, int length)
2503    {
2504        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2505        final byte[] result = allocIfNull(out, outOffset + len);
2506
2507        for (int i = 0; i < len; i++)
2508            result[i + outOffset] = (byte) in[i + inOffset];
2509
2510        return result;
2511    }
2512
2513    public static double[] shortArrayToDoubleArray(short[] in, int inOffset, double[] out, int outOffset, int length,
2514            boolean signed)
2515    {
2516        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2517        final double[] result = allocIfNull(out, outOffset + len);
2518
2519        if (signed)
2520        {
2521            for (int i = 0; i < len; i++)
2522                result[i + outOffset] = in[i + inOffset];
2523        }
2524        else
2525        {
2526            for (int i = 0; i < len; i++)
2527                result[i + outOffset] = TypeUtil.unsign(in[i + inOffset]);
2528        }
2529
2530        return result;
2531    }
2532
2533    public static float[] shortArrayToFloatArray(short[] in, int inOffset, float[] out, int outOffset, int length,
2534            boolean signed)
2535    {
2536        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2537        final float[] result = allocIfNull(out, outOffset + len);
2538
2539        if (signed)
2540        {
2541            for (int i = 0; i < len; i++)
2542                result[i + outOffset] = in[i + inOffset];
2543        }
2544        else
2545        {
2546            for (int i = 0; i < len; i++)
2547                result[i + outOffset] = TypeUtil.unsign(in[i + inOffset]);
2548        }
2549
2550        return result;
2551    }
2552
2553    public static long[] shortArrayToLongArray(short[] in, int inOffset, long[] out, int outOffset, int length,
2554            boolean signed)
2555    {
2556        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2557        final long[] result = allocIfNull(out, outOffset + len);
2558
2559        if (signed)
2560        {
2561            for (int i = 0; i < len; i++)
2562                result[i + outOffset] = in[i + inOffset];
2563        }
2564        else
2565        {
2566            for (int i = 0; i < len; i++)
2567                result[i + outOffset] = TypeUtil.unsignL(in[i + inOffset]);
2568        }
2569
2570        return result;
2571    }
2572
2573    public static int[] shortArrayToIntArray(short[] in, int inOffset, int[] out, int outOffset, int length,
2574            boolean signed)
2575    {
2576        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2577        final int[] result = allocIfNull(out, outOffset + len);
2578
2579        if (signed)
2580        {
2581            for (int i = 0; i < len; i++)
2582                result[i + outOffset] = in[i + inOffset];
2583        }
2584        else
2585        {
2586            for (int i = 0; i < len; i++)
2587                result[i + outOffset] = TypeUtil.unsign(in[i + inOffset]);
2588        }
2589
2590        return result;
2591    }
2592
2593    public static short[] shortArrayToShortArray(short[] in, int inOffset, short[] out, int outOffset, int length)
2594    {
2595        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2596        final short[] result = allocIfNull(out, outOffset + len);
2597
2598        System.arraycopy(in, inOffset, result, outOffset, len);
2599
2600        return result;
2601    }
2602
2603    public static byte[] shortArrayToByteArray(short[] in, int inOffset, byte[] out, int outOffset, int length)
2604    {
2605        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2606        final byte[] result = allocIfNull(out, outOffset + len);
2607
2608        for (int i = 0; i < len; i++)
2609            result[i + outOffset] = (byte) in[i + inOffset];
2610
2611        return result;
2612    }
2613
2614    public static double[] byteArrayToDoubleArray(byte[] in, int inOffset, double[] out, int outOffset, int length,
2615            boolean signed)
2616    {
2617        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2618        final double[] result = allocIfNull(out, outOffset + len);
2619
2620        if (signed)
2621        {
2622            for (int i = 0; i < len; i++)
2623                result[i + outOffset] = in[i + inOffset];
2624        }
2625        else
2626        {
2627            for (int i = 0; i < len; i++)
2628                result[i + outOffset] = TypeUtil.unsign(in[i + inOffset]);
2629        }
2630
2631        return result;
2632    }
2633
2634    public static float[] byteArrayToFloatArray(byte[] in, int inOffset, float[] out, int outOffset, int length,
2635            boolean signed)
2636    {
2637        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2638        final float[] result = allocIfNull(out, outOffset + len);
2639
2640        if (signed)
2641        {
2642            for (int i = 0; i < len; i++)
2643                result[i + outOffset] = in[i + inOffset];
2644        }
2645        else
2646        {
2647            for (int i = 0; i < len; i++)
2648                result[i + outOffset] = TypeUtil.unsign(in[i + inOffset]);
2649        }
2650
2651        return result;
2652    }
2653
2654    public static long[] byteArrayToLongArray(byte[] in, int inOffset, long[] out, int outOffset, int length,
2655            boolean signed)
2656    {
2657        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2658        final long[] result = allocIfNull(out, outOffset + len);
2659
2660        if (signed)
2661        {
2662            for (int i = 0; i < len; i++)
2663                result[i + outOffset] = in[i + inOffset];
2664        }
2665        else
2666        {
2667            for (int i = 0; i < len; i++)
2668                result[i + outOffset] = TypeUtil.unsignL(in[i + inOffset]);
2669        }
2670
2671        return result;
2672    }
2673
2674    public static int[] byteArrayToIntArray(byte[] in, int inOffset, int[] out, int outOffset, int length,
2675            boolean signed)
2676    {
2677        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2678        final int[] result = allocIfNull(out, outOffset + len);
2679
2680        if (signed)
2681        {
2682            for (int i = 0; i < len; i++)
2683                result[i + outOffset] = in[i + inOffset];
2684        }
2685        else
2686        {
2687            for (int i = 0; i < len; i++)
2688                result[i + outOffset] = TypeUtil.unsign(in[i + inOffset]);
2689        }
2690
2691        return result;
2692    }
2693
2694    public static short[] byteArrayToShortArray(byte[] in, int inOffset, short[] out, int outOffset, int length,
2695            boolean signed)
2696    {
2697        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2698        final short[] result = allocIfNull(out, outOffset + len);
2699
2700        if (signed)
2701        {
2702            for (int i = 0; i < len; i++)
2703                result[i + outOffset] = in[i + inOffset];
2704        }
2705        else
2706        {
2707            for (int i = 0; i < len; i++)
2708                result[i + outOffset] = (short) TypeUtil.unsign(in[i + inOffset]);
2709        }
2710
2711        return result;
2712    }
2713
2714    public static byte[] byteArrayToByteArray(byte[] in, int inOffset, byte[] out, int outOffset, int length)
2715    {
2716        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
2717        final byte[] result = allocIfNull(out, outOffset + len);
2718
2719        System.arraycopy(in, inOffset, result, outOffset, len);
2720
2721        return result;
2722    }
2723
2724    public static float[] doubleArrayToFloatArray(double[] array)
2725    {
2726        return doubleArrayToFloatArray(array, 0, null, 0, array.length);
2727    }
2728
2729    public static long[] doubleArrayToLongArray(double[] array)
2730    {
2731        return doubleArrayToLongArray(array, 0, null, 0, array.length);
2732    }
2733
2734    public static int[] doubleArrayToIntArray(double[] array)
2735    {
2736        return doubleArrayToIntArray(array, 0, null, 0, array.length);
2737    }
2738
2739    public static short[] doubleArrayToShortArray(double[] array)
2740    {
2741        return doubleArrayToShortArray(array, 0, null, 0, array.length);
2742    }
2743
2744    public static byte[] doubleArrayToByteArray(double[] array)
2745    {
2746        return doubleArrayToByteArray(array, 0, null, 0, array.length);
2747    }
2748
2749    public static double[] floatArrayToDoubleArray(float[] array)
2750    {
2751        return floatArrayToDoubleArray(array, 0, null, 0, array.length);
2752    }
2753
2754    public static long[] floatArrayToLongArray(float[] array)
2755    {
2756        return floatArrayToLongArray(array, 0, null, 0, array.length);
2757    }
2758
2759    public static int[] floatArrayToIntArray(float[] array)
2760    {
2761        return floatArrayToIntArray(array, 0, null, 0, array.length);
2762    }
2763
2764    public static short[] floatArrayToShortArray(float[] array)
2765    {
2766        return floatArrayToShortArray(array, 0, null, 0, array.length);
2767    }
2768
2769    public static byte[] floatArrayToByteArray(float[] array)
2770    {
2771        return floatArrayToByteArray(array, 0, null, 0, array.length);
2772    }
2773
2774    public static double[] longArrayToDoubleArray(long[] array, boolean signed)
2775    {
2776        return longArrayToDoubleArray(array, 0, null, 0, array.length, signed);
2777    }
2778
2779    public static float[] longArrayToFloatArray(long[] array, boolean signed)
2780    {
2781        return longArrayToFloatArray(array, 0, null, 0, array.length, signed);
2782    }
2783
2784    public static short[] longArrayToShortArray(long[] array)
2785    {
2786        return longArrayToShortArray(array, 0, null, 0, array.length);
2787    }
2788
2789    public static byte[] longArrayToByteArray(long[] array)
2790    {
2791        return longArrayToByteArray(array, 0, null, 0, array.length);
2792    }
2793
2794    public static double[] intArrayToDoubleArray(int[] array, boolean signed)
2795    {
2796        return intArrayToDoubleArray(array, 0, null, 0, array.length, signed);
2797    }
2798
2799    public static float[] intArrayToFloatArray(int[] array, boolean signed)
2800    {
2801        return intArrayToFloatArray(array, 0, null, 0, array.length, signed);
2802    }
2803
2804    public static long[] intArrayToLongArray(int[] array, boolean signed)
2805    {
2806        return intArrayToLongArray(array, 0, null, 0, array.length, signed);
2807    }
2808
2809    public static short[] intArrayToShortArray(int[] array)
2810    {
2811        return intArrayToShortArray(array, 0, null, 0, array.length);
2812    }
2813
2814    public static byte[] intArrayToByteArray(int[] array)
2815    {
2816        return intArrayToByteArray(array, 0, null, 0, array.length);
2817    }
2818
2819    public static double[] shortArrayToDoubleArray(short[] array, boolean signed)
2820    {
2821        return shortArrayToDoubleArray(array, 0, null, 0, array.length, signed);
2822    }
2823
2824    public static float[] shortArrayToFloatArray(short[] array, boolean signed)
2825    {
2826        return shortArrayToFloatArray(array, 0, null, 0, array.length, signed);
2827    }
2828
2829    public static long[] shortArrayToLongArray(short[] array, boolean signed)
2830    {
2831        return shortArrayToLongArray(array, 0, null, 0, array.length, signed);
2832    }
2833
2834    public static int[] shortArrayToIntArray(short[] array, boolean signed)
2835    {
2836        return shortArrayToIntArray(array, 0, null, 0, array.length, signed);
2837    }
2838
2839    public static byte[] shortArrayToByteArray(short[] array)
2840    {
2841        return shortArrayToByteArray(array, 0, null, 0, array.length);
2842    }
2843
2844    public static double[] byteArrayToDoubleArray(byte[] array, boolean signed)
2845    {
2846        return byteArrayToDoubleArray(array, 0, null, 0, array.length, signed);
2847    }
2848
2849    public static float[] byteArrayToFloatArray(byte[] array, boolean signed)
2850    {
2851        return byteArrayToFloatArray(array, 0, null, 0, array.length, signed);
2852    }
2853
2854    public static long[] byteArrayToLongArray(byte[] array, boolean signed)
2855    {
2856        return byteArrayToLongArray(array, 0, null, 0, array.length, signed);
2857    }
2858
2859    public static int[] byteArrayToIntArray(byte[] array, boolean signed)
2860    {
2861        return byteArrayToIntArray(array, 0, null, 0, array.length, signed);
2862    }
2863
2864    public static short[] byteArrayToShortArray(byte[] array, boolean signed)
2865    {
2866        return byteArrayToShortArray(array, 0, null, 0, array.length, signed);
2867    }
2868
2869    //
2870    //
2871    //
2872    //
2873    //
2874    //
2875    //
2876    //
2877
2878    public static Object doubleArrayToSafeArray(double[] in, int inOffset, Object out, int outOffset, int length,
2879            boolean signed)
2880    {
2881        switch (ArrayUtil.getDataType(out))
2882        {
2883            case BYTE:
2884                return doubleArrayToSafeByteArray(in, inOffset, (byte[]) out, outOffset, length, signed);
2885            case SHORT:
2886                return doubleArrayToSafeShortArray(in, inOffset, (short[]) out, outOffset, length, signed);
2887            case INT:
2888                return doubleArrayToSafeIntArray(in, inOffset, (int[]) out, outOffset, length, signed);
2889            case LONG:
2890                return doubleArrayToSafeLongArray(in, inOffset, (long[]) out, outOffset, length, signed);
2891            case FLOAT:
2892                return doubleArrayToFloatArray(in, inOffset, (float[]) out, outOffset, length);
2893            case DOUBLE:
2894                return doubleArrayToDoubleArray(in, inOffset, (double[]) out, outOffset, length);
2895            default:
2896                return out;
2897        }
2898    }
2899
2900    public static Object doubleArrayToSafeArray(double[] in, Object out, boolean signed)
2901    {
2902        return doubleArrayToSafeArray(in, 0, out, 0, -1, signed);
2903    }
2904
2905    public static Object floatArrayToSafeArray(float[] in, int inOffset, Object out, int outOffset, int length,
2906            boolean signed)
2907    {
2908        switch (ArrayUtil.getDataType(out))
2909        {
2910            case BYTE:
2911                return floatArrayToSafeByteArray(in, inOffset, (byte[]) out, outOffset, length, signed);
2912            case SHORT:
2913                return floatArrayToSafeShortArray(in, inOffset, (short[]) out, outOffset, length, signed);
2914            case INT:
2915                return floatArrayToSafeIntArray(in, inOffset, (int[]) out, outOffset, length, signed);
2916            case LONG:
2917                return floatArrayToSafeLongArray(in, inOffset, (long[]) out, outOffset, length, signed);
2918            case FLOAT:
2919                return floatArrayToFloatArray(in, inOffset, (float[]) out, outOffset, length);
2920            case DOUBLE:
2921                return floatArrayToDoubleArray(in, inOffset, (double[]) out, outOffset, length);
2922            default:
2923                return out;
2924        }
2925    }
2926
2927    public static Object floatArrayToSafeArray(float[] in, Object out, boolean signed)
2928    {
2929        return floatArrayToSafeArray(in, 0, out, 0, -1, signed);
2930    }
2931
2932    public static Object longArrayToSafeArray(long[] in, int inOffset, Object out, int outOffset, int length,
2933            boolean srcSigned, boolean dstSigned)
2934    {
2935        switch (ArrayUtil.getDataType(out))
2936        {
2937            case BYTE:
2938                return longArrayToSafeByteArray(in, inOffset, (byte[]) out, outOffset, length, srcSigned, dstSigned);
2939            case SHORT:
2940                return longArrayToSafeShortArray(in, inOffset, (short[]) out, outOffset, length, srcSigned, dstSigned);
2941            case INT:
2942                return longArrayToSafeIntArray(in, inOffset, (int[]) out, outOffset, length, srcSigned, dstSigned);
2943            case LONG:
2944                return longArrayToSafeLongArray(in, inOffset, (long[]) out, outOffset, length, srcSigned, dstSigned);
2945            case FLOAT:
2946                return longArrayToFloatArray(in, inOffset, (float[]) out, outOffset, length, srcSigned);
2947            case DOUBLE:
2948                return longArrayToDoubleArray(in, inOffset, (double[]) out, outOffset, length, srcSigned);
2949            default:
2950                return out;
2951        }
2952    }
2953
2954    public static Object longArrayToSafeArray(long[] in, Object out, boolean srcSigned, boolean dstSigned)
2955    {
2956        return longArrayToSafeArray(in, 0, out, 0, -1, srcSigned, dstSigned);
2957    }
2958
2959    /**
2960     * @deprecated Use {@link #longArrayToSafeArray(long[], int, Object, int, int, boolean, boolean)} instead.
2961     */
2962    @Deprecated
2963    public static Object longArrayToSafeArray(long[] in, int inOffset, Object out, int outOffset, int length,
2964            boolean signed)
2965    {
2966        return longArrayToSafeArray(in, inOffset, out, outOffset, length, signed, signed);
2967
2968    }
2969
2970    /**
2971     * @deprecated Use {@link #longArrayToSafeArray(long[], Object, boolean, boolean)} instead.
2972     */
2973    @Deprecated
2974    public static Object longArrayToSafeArray(long[] in, Object out, boolean signed)
2975    {
2976        return longArrayToSafeArray(in, 0, out, 0, -1, signed, signed);
2977    }
2978
2979    public static Object intArrayToSafeArray(int[] in, int inOffset, Object out, int outOffset, int length,
2980            boolean srcSigned, boolean dstSigned)
2981    {
2982        switch (ArrayUtil.getDataType(out))
2983        {
2984            case BYTE:
2985                return intArrayToSafeByteArray(in, inOffset, (byte[]) out, outOffset, length, srcSigned, dstSigned);
2986            case SHORT:
2987                return intArrayToSafeShortArray(in, inOffset, (short[]) out, outOffset, length, srcSigned, dstSigned);
2988            case INT:
2989                return intArrayToSafeIntArray(in, inOffset, (int[]) out, outOffset, length, srcSigned, dstSigned);
2990            case LONG:
2991                return intArrayToLongArray(in, inOffset, (long[]) out, outOffset, length, srcSigned);
2992            case FLOAT:
2993                return intArrayToFloatArray(in, inOffset, (float[]) out, outOffset, length, srcSigned);
2994            case DOUBLE:
2995                return intArrayToDoubleArray(in, inOffset, (double[]) out, outOffset, length, srcSigned);
2996            default:
2997                return out;
2998        }
2999    }
3000
3001    public static Object intArrayToSafeArray(int[] in, Object out, boolean srcSigned, boolean dstSigned)
3002    {
3003        return intArrayToSafeArray(in, 0, out, 0, -1, srcSigned, dstSigned);
3004    }
3005
3006    /**
3007     * @deprecated Use {@link #intArrayToSafeArray(int[], int, Object, int, int, boolean, boolean)} instead.
3008     */
3009    @Deprecated
3010    public static Object intArrayToSafeArray(int[] in, int inOffset, Object out, int outOffset, int length,
3011            boolean signed)
3012    {
3013        return intArrayToSafeArray(in, inOffset, out, outOffset, length, signed, signed);
3014    }
3015
3016    /**
3017     * @deprecated Use {@link #intArrayToSafeArray(int[], Object, boolean, boolean)} instead.
3018     */
3019    @Deprecated
3020    public static Object intArrayToSafeArray(int[] in, Object out, boolean signed)
3021    {
3022        return intArrayToSafeArray(in, 0, out, 0, -1, signed, signed);
3023    }
3024
3025    public static Object shortArrayToSafeArray(short[] in, int inOffset, Object out, int outOffset, int length,
3026            boolean srcSigned, boolean dstSigned)
3027    {
3028        switch (ArrayUtil.getDataType(out))
3029        {
3030            case BYTE:
3031                return shortArrayToSafeByteArray(in, inOffset, (byte[]) out, outOffset, length, srcSigned, dstSigned);
3032            case SHORT:
3033                return shortArrayToSafeShortArray(in, inOffset, (short[]) out, outOffset, length, srcSigned, dstSigned);
3034            case INT:
3035                return shortArrayToIntArray(in, inOffset, (int[]) out, outOffset, length, srcSigned);
3036            case LONG:
3037                return shortArrayToLongArray(in, inOffset, (long[]) out, outOffset, length, srcSigned);
3038            case FLOAT:
3039                return shortArrayToFloatArray(in, inOffset, (float[]) out, outOffset, length, srcSigned);
3040            case DOUBLE:
3041                return shortArrayToDoubleArray(in, inOffset, (double[]) out, outOffset, length, srcSigned);
3042            default:
3043                return out;
3044        }
3045    }
3046
3047    public static Object shortArrayToSafeArray(short[] in, Object out, boolean srcSigned, boolean dstSigned)
3048    {
3049        return shortArrayToSafeArray(in, 0, out, 0, -1, srcSigned, dstSigned);
3050    }
3051
3052    /**
3053     * @deprecated Use {@link #shortArrayToSafeArray(short[], int, Object, int, int, boolean, boolean)} instead.
3054     */
3055    @Deprecated
3056    public static Object shortArrayToSafeArray(short[] in, int inOffset, Object out, int outOffset, int length,
3057            boolean signed)
3058    {
3059        return shortArrayToSafeArray(in, inOffset, out, outOffset, length, signed, signed);
3060    }
3061
3062    /**
3063     * @deprecated Use {@link #shortArrayToSafeArray(short[], Object, boolean, boolean)} instead.
3064     */
3065    @Deprecated
3066    public static Object shortArrayToSafeArray(short[] in, Object out, boolean signed)
3067    {
3068        return shortArrayToSafeArray(in, 0, out, 0, -1, signed, signed);
3069
3070    }
3071
3072    public static Object byteArrayToSafeArray(byte[] in, int inOffset, Object out, int outOffset, int length,
3073            boolean srcSigned, boolean dstSigned)
3074    {
3075        switch (ArrayUtil.getDataType(out))
3076        {
3077            case BYTE:
3078                return byteArrayToSafeByteArray(in, inOffset, (byte[]) out, outOffset, length, srcSigned, dstSigned);
3079            case SHORT:
3080                return byteArrayToShortArray(in, inOffset, (short[]) out, outOffset, length, srcSigned);
3081            case INT:
3082                return byteArrayToIntArray(in, inOffset, (int[]) out, outOffset, length, srcSigned);
3083            case LONG:
3084                return byteArrayToLongArray(in, inOffset, (long[]) out, outOffset, length, srcSigned);
3085            case FLOAT:
3086                return byteArrayToFloatArray(in, inOffset, (float[]) out, outOffset, length, srcSigned);
3087            case DOUBLE:
3088                return byteArrayToDoubleArray(in, inOffset, (double[]) out, outOffset, length, srcSigned);
3089            default:
3090                return out;
3091        }
3092    }
3093
3094    public static Object byteArrayToSafeArray(byte[] in, Object out, boolean srcSigned, boolean dstSigned)
3095    {
3096        return byteArrayToSafeArray(in, 0, out, 0, -1, srcSigned, dstSigned);
3097    }
3098
3099    public static long[] arrayToSafeLongArray(Object in, int inOffset, long[] out, int outOffset, int length,
3100            boolean srcSigned, boolean dstSigned)
3101    {
3102        switch (ArrayUtil.getDataType(in))
3103        {
3104            case BYTE:
3105                return byteArrayToLongArray((byte[]) in, inOffset, out, outOffset, length, srcSigned);
3106            case SHORT:
3107                return shortArrayToLongArray((short[]) in, inOffset, out, outOffset, length, srcSigned);
3108            case INT:
3109                return intArrayToLongArray((int[]) in, inOffset, out, outOffset, length, srcSigned);
3110            case LONG:
3111                return longArrayToSafeLongArray((long[]) in, inOffset, out, outOffset, length, srcSigned, dstSigned);
3112            case FLOAT:
3113                return floatArrayToSafeLongArray((float[]) in, inOffset, out, outOffset, length, dstSigned);
3114            case DOUBLE:
3115                return doubleArrayToSafeLongArray((double[]) in, inOffset, out, outOffset, length, dstSigned);
3116            default:
3117                return out;
3118        }
3119    }
3120
3121    public static long[] arrayToSafeLongArray(Object in, long[] out, boolean srcSigned, boolean dstSigned)
3122    {
3123        return arrayToSafeLongArray(in, 0, out, 0, -1, srcSigned, dstSigned);
3124    }
3125
3126    /**
3127     * @deprecated Use {@link #arrayToSafeLongArray(Object, int, long[], int, int, boolean, boolean)} instead.
3128     */
3129    @Deprecated
3130    public static long[] arrayToSafeLongArray(Object in, int inOffset, long[] out, int outOffset, int length,
3131            boolean signed)
3132    {
3133        return arrayToSafeLongArray(in, inOffset, out, outOffset, length, signed, signed);
3134    }
3135
3136    /**
3137     * @deprecated Use {@link #arrayToSafeLongArray(Object, long[], boolean, boolean)} instead.
3138     */
3139    @Deprecated
3140    public static long[] arrayToSafeLongArray(Object in, long[] out, boolean signed)
3141    {
3142        return arrayToSafeLongArray(in, 0, out, 0, -1, signed, signed);
3143    }
3144
3145    public static int[] arrayToSafeIntArray(Object in, int inOffset, int[] out, int outOffset, int length,
3146            boolean srcSigned, boolean dstSigned)
3147    {
3148        switch (ArrayUtil.getDataType(in))
3149        {
3150            case BYTE:
3151                return byteArrayToIntArray((byte[]) in, inOffset, out, outOffset, length, srcSigned);
3152            case SHORT:
3153                return shortArrayToIntArray((short[]) in, inOffset, out, outOffset, length, srcSigned);
3154            case INT:
3155                return intArrayToSafeIntArray((int[]) in, inOffset, out, outOffset, length, srcSigned, dstSigned);
3156            case LONG:
3157                return longArrayToSafeIntArray((long[]) in, inOffset, out, outOffset, length, srcSigned, dstSigned);
3158            case FLOAT:
3159                return floatArrayToSafeIntArray((float[]) in, inOffset, out, outOffset, length, dstSigned);
3160            case DOUBLE:
3161                return doubleArrayToSafeIntArray((double[]) in, inOffset, out, outOffset, length, dstSigned);
3162            default:
3163                return out;
3164        }
3165    }
3166
3167    public static int[] arrayToSafeIntArray(Object in, int[] out, boolean srcSigned, boolean dstSigned)
3168    {
3169        return arrayToSafeIntArray(in, 0, out, 0, -1, srcSigned, dstSigned);
3170    }
3171
3172    /**
3173     * @deprecated Use {@link #arrayToSafeIntArray(Object, int, int[], int, int, boolean, boolean)} instead.
3174     */
3175    @Deprecated
3176    public static int[] arrayToSafeIntArray(Object in, int inOffset, int[] out, int outOffset, int length,
3177            boolean signed)
3178    {
3179        return arrayToSafeIntArray(in, inOffset, out, outOffset, length, signed, signed);
3180    }
3181
3182    /**
3183     * @deprecated Use {@link #arrayToSafeIntArray(Object, int[], boolean, boolean)} instead.
3184     */
3185    @Deprecated
3186    public static int[] arrayToSafeIntArray(Object in, int[] out, boolean signed)
3187    {
3188        return arrayToSafeIntArray(in, 0, out, 0, -1, signed, signed);
3189    }
3190
3191    public static short[] arrayToSafeShortArray(Object in, int inOffset, short[] out, int outOffset, int length,
3192            boolean srcSigned, boolean dstSigned)
3193    {
3194        switch (ArrayUtil.getDataType(in))
3195        {
3196            case BYTE:
3197                return byteArrayToShortArray((byte[]) in, inOffset, out, outOffset, length, srcSigned);
3198            case SHORT:
3199                return shortArrayToSafeShortArray((short[]) in, inOffset, out, outOffset, length, srcSigned, dstSigned);
3200            case INT:
3201                return intArrayToSafeShortArray((int[]) in, inOffset, out, outOffset, length, srcSigned, dstSigned);
3202            case LONG:
3203                return longArrayToSafeShortArray((long[]) in, inOffset, out, outOffset, length, srcSigned, dstSigned);
3204            case FLOAT:
3205                return floatArrayToSafeShortArray((float[]) in, inOffset, out, outOffset, length, dstSigned);
3206            case DOUBLE:
3207                return doubleArrayToSafeShortArray((double[]) in, inOffset, out, outOffset, length, dstSigned);
3208            default:
3209                return out;
3210        }
3211    }
3212
3213    public static short[] arrayToSafeShortArray(Object in, short[] out, boolean srcSigned, boolean dstSigned)
3214    {
3215        return arrayToSafeShortArray(in, 0, out, 0, -1, srcSigned, dstSigned);
3216    }
3217
3218    /**
3219     * @deprecated Use {@link #arrayToSafeShortArray(Object, int, short[], int, int, boolean, boolean)} instead.
3220     */
3221    @Deprecated
3222    public static short[] arrayToSafeShortArray(Object in, int inOffset, short[] out, int outOffset, int length,
3223            boolean signed)
3224    {
3225        return arrayToSafeShortArray(in, inOffset, out, outOffset, length, signed, signed);
3226    }
3227
3228    /**
3229     * @deprecated Use {@link #arrayToSafeShortArray(Object, short[], boolean, boolean)} instead.
3230     */
3231    @Deprecated
3232    public static short[] arrayToSafeShortArray(Object in, short[] out, boolean signed)
3233    {
3234        return arrayToSafeShortArray(in, 0, out, 0, -1, signed, signed);
3235    }
3236
3237    public static byte[] arrayToSafeByteArray(Object in, int inOffset, byte[] out, int outOffset, int length,
3238            boolean srcSigned, boolean dstSigned)
3239    {
3240        switch (ArrayUtil.getDataType(in))
3241        {
3242            case BYTE:
3243                return byteArrayToSafeByteArray((byte[]) in, inOffset, out, outOffset, length, srcSigned, dstSigned);
3244            case SHORT:
3245                return shortArrayToSafeByteArray((short[]) in, inOffset, out, outOffset, length, srcSigned, dstSigned);
3246            case INT:
3247                return intArrayToSafeByteArray((int[]) in, inOffset, out, outOffset, length, srcSigned, dstSigned);
3248            case LONG:
3249                return longArrayToSafeByteArray((long[]) in, inOffset, out, outOffset, length, srcSigned, dstSigned);
3250            case FLOAT:
3251                return floatArrayToSafeByteArray((float[]) in, inOffset, out, outOffset, length, dstSigned);
3252            case DOUBLE:
3253                return doubleArrayToSafeByteArray((double[]) in, inOffset, out, outOffset, length, dstSigned);
3254            default:
3255                return out;
3256        }
3257    }
3258
3259    public static byte[] arrayToSafeByteArray(Object in, byte[] out, boolean srcSigned, boolean dstSigned)
3260    {
3261        return arrayToSafeByteArray(in, 0, out, 0, -1, srcSigned, dstSigned);
3262    }
3263
3264    /**
3265     * @deprecated Use {@link #arrayToSafeByteArray(Object, int, byte[], int, int, boolean, boolean)} instead.
3266     */
3267    @Deprecated
3268    public static byte[] arrayToSafeByteArray(Object in, int inOffset, byte[] out, int outOffset, int length,
3269            boolean signed)
3270    {
3271        return arrayToSafeByteArray(in, inOffset, out, outOffset, length, signed, signed);
3272    }
3273
3274    /**
3275     * @deprecated Use {@link #arrayToSafeByteArray(Object, byte[], boolean, boolean)} instead.
3276     */
3277    @Deprecated
3278    public static byte[] arrayToSafeByteArray(Object in, byte[] out, boolean signed)
3279    {
3280        return arrayToSafeByteArray(in, 0, out, 0, -1, signed, signed);
3281    }
3282
3283    //
3284    //
3285    //
3286    //
3287    //
3288    //
3289    //
3290    //
3291    //
3292    //
3293    //
3294    //
3295    //
3296    //
3297    //
3298    //
3299    //
3300    //
3301    //
3302    //
3303    //
3304    //
3305    //
3306    //
3307    //
3308    //
3309
3310    public static long[] doubleArrayToSafeLongArray(double[] in, int inOffset, long[] out, int outOffset, int length,
3311            boolean signed)
3312    {
3313        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3314        final long[] outArray = allocIfNull(out, outOffset + len);
3315
3316        if (signed)
3317        {
3318            // by default value is clamped to [Long.MIN_VALUE..Long.MAX_VALUE] range
3319            for (int i = 0; i < len; i++)
3320                outArray[i + outOffset] = (long) in[i + inOffset];
3321        }
3322        else
3323        {
3324            final double minValue = 0d;
3325            final double maxValue = DataType.ULONG_MAX_VALUE;
3326            final long minValueT = 0L;
3327            final long maxValueT = 0xFFFFFFFFFFFFFFFFL;
3328
3329            for (int i = 0; i < len; i++)
3330            {
3331                final double value = in[i + inOffset];
3332                final long result;
3333
3334                if (value >= maxValue)
3335                    result = maxValueT;
3336                else if (value <= minValue)
3337                    result = minValueT;
3338                else
3339                    result = TypeUtil.toLong(value);
3340
3341                outArray[i + outOffset] = result;
3342            }
3343        }
3344
3345        return outArray;
3346    }
3347
3348    public static int[] doubleArrayToSafeIntArray(double[] in, int inOffset, int[] out, int outOffset, int length,
3349            boolean signed)
3350    {
3351        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3352        final int[] outArray = allocIfNull(out, outOffset + len);
3353
3354        if (signed)
3355        {
3356            // by default value is clamped to [Integer.MIN_VALUE..Integer.MAX_VALUE] range
3357            for (int i = 0; i < len; i++)
3358                outArray[i + outOffset] = (int) in[i + inOffset];
3359        }
3360        else
3361        {
3362            final double minValue = 0d;
3363            final double maxValue = DataType.UINT_MAX_VALUE;
3364            final int minValueT = 0;
3365            final int maxValueT = 0xFFFFFFFF;
3366
3367            for (int i = 0; i < len; i++)
3368            {
3369                final double value = in[i + inOffset];
3370                final int result;
3371
3372                if (value >= maxValue)
3373                    result = maxValueT;
3374                else if (value <= minValue)
3375                    result = minValueT;
3376                else
3377                    result = TypeUtil.toInt(value);
3378
3379                outArray[i + outOffset] = result;
3380            }
3381        }
3382
3383        return outArray;
3384    }
3385
3386    public static short[] doubleArrayToSafeShortArray(double[] in, int inOffset, short[] out, int outOffset, int length,
3387            boolean signed)
3388    {
3389        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3390        final short[] outArray = allocIfNull(out, outOffset + len);
3391
3392        final double minValue;
3393        final double maxValue;
3394
3395        if (signed)
3396        {
3397            minValue = DataType.SHORT.getMinValue();
3398            maxValue = DataType.SHORT.getMaxValue();
3399        }
3400        else
3401        {
3402            minValue = DataType.USHORT.getMinValue();
3403            maxValue = DataType.USHORT.getMaxValue();
3404        }
3405
3406        final short minValueT = (short) minValue;
3407        final short maxValueT = (short) maxValue;
3408
3409        for (int i = 0; i < len; i++)
3410        {
3411            final double value = in[i + inOffset];
3412            final short result;
3413
3414            if (value >= maxValue)
3415                result = maxValueT;
3416            else if (value <= minValue)
3417                result = minValueT;
3418            else
3419                result = (short) value;
3420
3421            outArray[i + outOffset] = result;
3422        }
3423
3424        return outArray;
3425    }
3426
3427    public static byte[] doubleArrayToSafeByteArray(double[] in, int inOffset, byte[] out, int outOffset, int length,
3428            boolean signed)
3429    {
3430        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3431        final byte[] outArray = allocIfNull(out, outOffset + len);
3432
3433        final double minValue;
3434        final double maxValue;
3435
3436        if (signed)
3437        {
3438            minValue = DataType.BYTE.getMinValue();
3439            maxValue = DataType.BYTE.getMaxValue();
3440        }
3441        else
3442        {
3443            minValue = DataType.UBYTE.getMinValue();
3444            maxValue = DataType.UBYTE.getMaxValue();
3445        }
3446
3447        final byte minValueT = (byte) minValue;
3448        final byte maxValueT = (byte) maxValue;
3449
3450        for (int i = 0; i < len; i++)
3451        {
3452            final double value = in[i + inOffset];
3453            final byte result;
3454
3455            if (value >= maxValue)
3456                result = maxValueT;
3457            else if (value <= minValue)
3458                result = minValueT;
3459            else
3460                result = (byte) value;
3461
3462            outArray[i + outOffset] = result;
3463        }
3464
3465        return outArray;
3466    }
3467
3468    public static long[] floatArrayToSafeLongArray(float[] in, int inOffset, long[] out, int outOffset, int length,
3469            boolean signed)
3470    {
3471        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3472        final long[] outArray = allocIfNull(out, outOffset + len);
3473
3474        if (signed)
3475        {
3476            // by default value is clamped to [Long.MIN_VALUE..Long.MAX_VALUE] range
3477            for (int i = 0; i < len; i++)
3478                outArray[i + outOffset] = (long) in[i + inOffset];
3479        }
3480        else
3481        {
3482            final float minValue = 0f;
3483            final float maxValue = DataType.ULONG_MAX_VALUE_F;
3484            final long minValueT = 0L;
3485            final long maxValueT = 0xFFFFFFFFFFFFFFFFL;
3486
3487            for (int i = 0; i < len; i++)
3488            {
3489                final float value = in[i + inOffset];
3490                final long result;
3491
3492                if (value >= maxValue)
3493                    result = maxValueT;
3494                else if (value <= minValue)
3495                    result = minValueT;
3496                else
3497                    result = TypeUtil.toLong(value);
3498
3499                outArray[i + outOffset] = result;
3500            }
3501        }
3502
3503        return outArray;
3504    }
3505
3506    public static int[] floatArrayToSafeIntArray(float[] in, int inOffset, int[] out, int outOffset, int length,
3507            boolean signed)
3508    {
3509        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3510        final int[] outArray = allocIfNull(out, outOffset + len);
3511
3512        if (signed)
3513        {
3514            // by default value is clamped to [Integer.MIN_VALUE..Integer.MAX_VALUE] range
3515            for (int i = 0; i < len; i++)
3516                outArray[i + outOffset] = (int) in[i + inOffset];
3517        }
3518        else
3519        {
3520            final float minValue = 0f;
3521            final float maxValue = DataType.UINT_MAX_VALUE_F;
3522            final int minValueT = 0;
3523            final int maxValueT = 0xFFFFFFFF;
3524
3525            for (int i = 0; i < len; i++)
3526            {
3527                final float value = in[i + inOffset];
3528                final int result;
3529
3530                if (value >= maxValue)
3531                    result = maxValueT;
3532                else if (value <= minValue)
3533                    result = minValueT;
3534                else
3535                    result = TypeUtil.toInt(value);
3536
3537                outArray[i + outOffset] = result;
3538            }
3539        }
3540
3541        return outArray;
3542    }
3543
3544    public static short[] floatArrayToSafeShortArray(float[] in, int inOffset, short[] out, int outOffset, int length,
3545            boolean signed)
3546    {
3547        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3548        final short[] outArray = allocIfNull(out, outOffset + len);
3549
3550        final float minValue;
3551        final float maxValue;
3552
3553        if (signed)
3554        {
3555            minValue = (float) DataType.SHORT.getMinValue();
3556            maxValue = (float) DataType.SHORT.getMaxValue();
3557        }
3558        else
3559        {
3560            minValue = (float) DataType.USHORT.getMinValue();
3561            maxValue = (float) DataType.USHORT.getMaxValue();
3562        }
3563
3564        final short minValueT = (short) minValue;
3565        final short maxValueT = (short) maxValue;
3566
3567        for (int i = 0; i < len; i++)
3568        {
3569            final float value = in[i + inOffset];
3570            final short result;
3571
3572            if (value >= maxValue)
3573                result = maxValueT;
3574            else if (value <= minValue)
3575                result = minValueT;
3576            else
3577                result = (short) value;
3578
3579            outArray[i + outOffset] = result;
3580        }
3581
3582        return outArray;
3583    }
3584
3585    public static byte[] floatArrayToSafeByteArray(float[] in, int inOffset, byte[] out, int outOffset, int length,
3586            boolean signed)
3587    {
3588        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3589        final byte[] outArray = allocIfNull(out, outOffset + len);
3590
3591        final float minValue;
3592        final float maxValue;
3593
3594        if (signed)
3595        {
3596            minValue = (float) DataType.BYTE.getMinValue();
3597            maxValue = (float) DataType.BYTE.getMaxValue();
3598        }
3599        else
3600        {
3601            minValue = (float) DataType.UBYTE.getMinValue();
3602            maxValue = (float) DataType.UBYTE.getMaxValue();
3603        }
3604
3605        final byte minValueT = (byte) minValue;
3606        final byte maxValueT = (byte) maxValue;
3607
3608        for (int i = 0; i < len; i++)
3609        {
3610            final float value = in[i + inOffset];
3611            final byte result;
3612
3613            if (value >= maxValue)
3614                result = maxValueT;
3615            else if (value <= minValue)
3616                result = minValueT;
3617            else
3618                result = (byte) value;
3619
3620            outArray[i + outOffset] = result;
3621        }
3622
3623        return outArray;
3624    }
3625
3626    public static long[] longArrayToSafeLongArray(long[] in, int inOffset, long[] out, int outOffset, int length,
3627            boolean srcSigned, boolean dstSigned)
3628    {
3629        // same sign ?
3630        if (srcSigned == dstSigned)
3631            return longArrayToLongArray(in, inOffset, out, outOffset, length);
3632
3633        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3634        final long[] outArray = allocIfNull(out, outOffset + len);
3635        final long maxValue = Long.MAX_VALUE;
3636
3637        for (int i = 0; i < len; i++)
3638        {
3639            long value = in[i + inOffset];
3640
3641            // signed and unsigned on other side --> need to clamp
3642            if (value < 0)
3643            {
3644                if (srcSigned)
3645                    value = 0;
3646                else
3647                    value = maxValue;
3648            }
3649
3650            outArray[i + outOffset] = value;
3651        }
3652
3653        return outArray;
3654    }
3655
3656    public static int[] longArrayToSafeIntArray(long[] in, int inOffset, int[] out, int outOffset, int length,
3657            boolean srcSigned, boolean dstSigned)
3658    {
3659        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3660        final int[] outArray = allocIfNull(out, outOffset + len);
3661
3662        final long minValue;
3663        final long maxValue;
3664
3665        if (dstSigned)
3666        {
3667            minValue = (long) DataType.INT.getMinValue();
3668            maxValue = (long) DataType.INT.getMaxValue();
3669        }
3670        else
3671        {
3672            minValue = (long) DataType.UINT.getMinValue();
3673            maxValue = (long) DataType.UINT.getMaxValue();
3674        }
3675
3676        final int minValueT = (int) minValue;
3677        final int maxValueT = (int) maxValue;
3678
3679        for (int i = 0; i < len; i++)
3680        {
3681            final long value = in[i + inOffset];
3682            final int result;
3683
3684            if ((!srcSigned) && (value < 0))
3685                result = maxValueT;
3686            else if (value >= maxValue)
3687                result = maxValueT;
3688            else if (value <= minValue)
3689                result = minValueT;
3690            else
3691                result = (int) value;
3692
3693            outArray[i + outOffset] = result;
3694        }
3695
3696        return outArray;
3697    }
3698
3699    public static short[] longArrayToSafeShortArray(long[] in, int inOffset, short[] out, int outOffset, int length,
3700            boolean srcSigned, boolean dstSigned)
3701    {
3702        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3703        final short[] outArray = allocIfNull(out, outOffset + len);
3704
3705        final long minValue;
3706        final long maxValue;
3707
3708        if (dstSigned)
3709        {
3710            minValue = (long) DataType.SHORT.getMinValue();
3711            maxValue = (long) DataType.SHORT.getMaxValue();
3712        }
3713        else
3714        {
3715            minValue = (long) DataType.USHORT.getMinValue();
3716            maxValue = (long) DataType.USHORT.getMaxValue();
3717        }
3718
3719        final short minValueT = (short) minValue;
3720        final short maxValueT = (short) maxValue;
3721
3722        for (int i = 0; i < len; i++)
3723        {
3724            final long value = in[i + inOffset];
3725            final short result;
3726
3727            if ((!srcSigned) && (value < 0))
3728                result = maxValueT;
3729            else if (value >= maxValue)
3730                result = maxValueT;
3731            else if (value <= minValue)
3732                result = minValueT;
3733            else
3734                result = (short) value;
3735
3736            outArray[i + outOffset] = result;
3737        }
3738
3739        return outArray;
3740    }
3741
3742    public static byte[] longArrayToSafeByteArray(long[] in, int inOffset, byte[] out, int outOffset, int length,
3743            boolean srcSigned, boolean dstSigned)
3744    {
3745        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3746        final byte[] outArray = allocIfNull(out, outOffset + len);
3747
3748        final long minValue;
3749        final long maxValue;
3750
3751        if (dstSigned)
3752        {
3753            minValue = (long) DataType.BYTE.getMinValue();
3754            maxValue = (long) DataType.BYTE.getMaxValue();
3755        }
3756        else
3757        {
3758            minValue = (long) DataType.UBYTE.getMinValue();
3759            maxValue = (long) DataType.UBYTE.getMaxValue();
3760        }
3761
3762        final byte minValueT = (byte) minValue;
3763        final byte maxValueT = (byte) maxValue;
3764
3765        for (int i = 0; i < len; i++)
3766        {
3767            final long value = in[i + inOffset];
3768            final byte result;
3769
3770            if ((!srcSigned) && (value < 0))
3771                result = maxValueT;
3772            else if (value >= maxValue)
3773                result = maxValueT;
3774            else if (value <= minValue)
3775                result = minValueT;
3776            else
3777                result = (byte) value;
3778
3779            outArray[i + outOffset] = result;
3780        }
3781
3782        return outArray;
3783    }
3784
3785    /**
3786     * @deprecated Use {@link #longArrayToSafeIntArray(long[], int, int[], int, int, boolean, boolean)} instead.
3787     */
3788    @Deprecated
3789    public static int[] longArrayToSafeIntArray(long[] in, int inOffset, int[] out, int outOffset, int length,
3790            boolean signed)
3791    {
3792        return longArrayToSafeIntArray(in, inOffset, out, outOffset, length, signed, signed);
3793    }
3794
3795    /**
3796     * @deprecated Use {@link #longArrayToSafeShortArray(long[], int, short[], int, int, boolean, boolean)} instead.
3797     */
3798    @Deprecated
3799    public static short[] longArrayToSafeShortArray(long[] in, int inOffset, short[] out, int outOffset, int length,
3800            boolean signed)
3801    {
3802        return longArrayToSafeShortArray(in, inOffset, out, outOffset, length, signed, signed);
3803    }
3804
3805    /**
3806     * @deprecated Use {@link #longArrayToSafeByteArray(long[], int, byte[], int, int, boolean, boolean)} instead.
3807     */
3808    @Deprecated
3809    public static byte[] longArrayToSafeByteArray(long[] in, int inOffset, byte[] out, int outOffset, int length,
3810            boolean signed)
3811    {
3812        return longArrayToSafeByteArray(in, inOffset, out, outOffset, length, signed, signed);
3813    }
3814
3815    public static int[] intArrayToSafeIntArray(int[] in, int inOffset, int[] out, int outOffset, int length,
3816            boolean srcSigned, boolean dstSigned)
3817    {
3818        // same sign ?
3819        if (srcSigned == dstSigned)
3820            return intArrayToIntArray(in, inOffset, out, outOffset, length);
3821
3822        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3823        final int[] outArray = allocIfNull(out, outOffset + len);
3824        final int maxValue = Integer.MAX_VALUE;
3825
3826        for (int i = 0; i < len; i++)
3827        {
3828            int value = in[i + inOffset];
3829
3830            // signed and unsigned on other side --> need to clamp
3831            if (value < 0)
3832            {
3833                if (srcSigned)
3834                    value = 0;
3835                else
3836                    value = maxValue;
3837            }
3838
3839            outArray[i + outOffset] = value;
3840        }
3841
3842        return outArray;
3843    }
3844
3845    public static short[] intArrayToSafeShortArray(int[] in, int inOffset, short[] out, int outOffset, int length,
3846            boolean srcSigned, boolean dstSigned)
3847    {
3848        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3849        final short[] outArray = allocIfNull(out, outOffset + len);
3850
3851        final int minValue;
3852        final int maxValue;
3853
3854        if (dstSigned)
3855        {
3856            minValue = (int) DataType.SHORT.getMinValue();
3857            maxValue = (int) DataType.SHORT.getMaxValue();
3858        }
3859        else
3860        {
3861            minValue = (int) DataType.USHORT.getMinValue();
3862            maxValue = (int) DataType.USHORT.getMaxValue();
3863        }
3864
3865        final short minValueT = (short) minValue;
3866        final short maxValueT = (short) maxValue;
3867
3868        for (int i = 0; i < len; i++)
3869        {
3870            final int value = in[i + inOffset];
3871            final short result;
3872
3873            if ((!srcSigned) && (value < 0))
3874                result = maxValueT;
3875            else if (value >= maxValue)
3876                result = maxValueT;
3877            else if (value <= minValue)
3878                result = minValueT;
3879            else
3880                result = (short) value;
3881
3882            outArray[i + outOffset] = result;
3883        }
3884
3885        return outArray;
3886    }
3887
3888    public static byte[] intArrayToSafeByteArray(int[] in, int inOffset, byte[] out, int outOffset, int length,
3889            boolean srcSigned, boolean dstSigned)
3890    {
3891        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3892        final byte[] outArray = allocIfNull(out, outOffset + len);
3893
3894        final int minValue;
3895        final int maxValue;
3896
3897        if (dstSigned)
3898        {
3899            minValue = (int) DataType.BYTE.getMinValue();
3900            maxValue = (int) DataType.BYTE.getMaxValue();
3901        }
3902        else
3903        {
3904            minValue = (int) DataType.UBYTE.getMinValue();
3905            maxValue = (int) DataType.UBYTE.getMaxValue();
3906        }
3907
3908        final byte minValueT = (byte) minValue;
3909        final byte maxValueT = (byte) maxValue;
3910
3911        for (int i = 0; i < len; i++)
3912        {
3913            final int value = in[i + inOffset];
3914            final byte result;
3915
3916            if ((!srcSigned) && (value < 0))
3917                result = maxValueT;
3918            else if (value >= maxValue)
3919                result = maxValueT;
3920            else if (value <= minValue)
3921                result = minValueT;
3922            else
3923                result = (byte) value;
3924
3925            outArray[i + outOffset] = result;
3926        }
3927
3928        return outArray;
3929    }
3930
3931    /**
3932     * @deprecated Use {@link #intArrayToSafeShortArray(int[], int, short[], int, int, boolean, boolean)} instead.
3933     */
3934    @Deprecated
3935    public static short[] intArrayToSafeShortArray(int[] in, int inOffset, short[] out, int outOffset, int length,
3936            boolean signed)
3937    {
3938        return intArrayToSafeShortArray(in, inOffset, out, outOffset, length, signed, signed);
3939
3940    }
3941
3942    /**
3943     * @deprecated Use {@link #intArrayToSafeByteArray(int[], int, byte[], int, int, boolean, boolean)} instead.
3944     */
3945    @Deprecated
3946    public static byte[] intArrayToSafeByteArray(int[] in, int inOffset, byte[] out, int outOffset, int length,
3947            boolean signed)
3948    {
3949        return intArrayToSafeByteArray(in, inOffset, out, outOffset, length, signed, signed);
3950    }
3951
3952    public static short[] shortArrayToSafeShortArray(short[] in, int inOffset, short[] out, int outOffset, int length,
3953            boolean srcSigned, boolean dstSigned)
3954    {
3955        // same sign ?
3956        if (srcSigned == dstSigned)
3957            return shortArrayToShortArray(in, inOffset, out, outOffset, length);
3958
3959        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3960        final short[] outArray = allocIfNull(out, outOffset + len);
3961        final short maxValue = Short.MAX_VALUE;
3962
3963        for (int i = 0; i < len; i++)
3964        {
3965            short value = in[i + inOffset];
3966
3967            // signed and unsigned on other side --> need to clamp
3968            if (value < 0)
3969            {
3970                if (srcSigned)
3971                    value = 0;
3972                else
3973                    value = maxValue;
3974            }
3975
3976            outArray[i + outOffset] = value;
3977        }
3978
3979        return outArray;
3980    }
3981
3982    public static byte[] shortArrayToSafeByteArray(short[] in, int inOffset, byte[] out, int outOffset, int length,
3983            boolean srcSigned, boolean dstSigned)
3984    {
3985        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
3986        final byte[] outArray = allocIfNull(out, outOffset + len);
3987
3988        final short minValue;
3989        final short maxValue;
3990
3991        if (dstSigned)
3992        {
3993            minValue = (short) DataType.BYTE.getMinValue();
3994            maxValue = (short) DataType.BYTE.getMaxValue();
3995        }
3996        else
3997        {
3998            minValue = (short) DataType.UBYTE.getMinValue();
3999            maxValue = (short) DataType.UBYTE.getMaxValue();
4000        }
4001
4002        final byte minValueT = (byte) minValue;
4003        final byte maxValueT = (byte) maxValue;
4004
4005        for (int i = 0; i < len; i++)
4006        {
4007            final short value = in[i + inOffset];
4008            final byte result;
4009
4010            if ((!srcSigned) && (value < 0))
4011                result = maxValueT;
4012            else if (value >= maxValue)
4013                result = maxValueT;
4014            else if (value <= minValue)
4015                result = minValueT;
4016            else
4017                result = (byte) value;
4018
4019            outArray[i + outOffset] = result;
4020        }
4021
4022        return outArray;
4023    }
4024
4025    /**
4026     * @deprecated Use {@link #shortArrayToSafeByteArray(short[], int, byte[], int, int, boolean, boolean)} instead.
4027     */
4028    @Deprecated
4029    public static byte[] shortArrayToSafeByteArray(short[] in, int inOffset, byte[] out, int outOffset, int length,
4030            boolean signed)
4031    {
4032        return shortArrayToSafeByteArray(in, inOffset, out, outOffset, length, signed, signed);
4033    }
4034
4035    public static byte[] byteArrayToSafeByteArray(byte[] in, int inOffset, byte[] out, int outOffset, int length,
4036            boolean srcSigned, boolean dstSigned)
4037    {
4038        // same sign ?
4039        if (srcSigned == dstSigned)
4040            return byteArrayToByteArray(in, inOffset, out, outOffset, length);
4041
4042        final int len = ArrayUtil.getCopyLength(in, inOffset, out, outOffset, length);
4043        final byte[] outArray = allocIfNull(out, outOffset + len);
4044        final byte maxValue = Byte.MAX_VALUE;
4045
4046        for (int i = 0; i < len; i++)
4047        {
4048            byte value = in[i + inOffset];
4049
4050            // signed and unsigned on other side --> need to clamp
4051            if (value < 0)
4052            {
4053                if (srcSigned)
4054                    value = 0;
4055                else
4056                    value = maxValue;
4057            }
4058
4059            outArray[i + outOffset] = value;
4060        }
4061
4062        return outArray;
4063    }
4064
4065    //
4066    //
4067    //
4068    //
4069    //
4070    //
4071    //
4072
4073    public static long[] doubleArrayToSafeLongArray(double[] array, boolean signed)
4074    {
4075        return doubleArrayToSafeLongArray(array, 0, null, 0, array.length, signed);
4076    }
4077
4078    public static int[] doubleArrayToSafeIntArray(double[] array, boolean signed)
4079    {
4080        return doubleArrayToSafeIntArray(array, 0, null, 0, array.length, signed);
4081    }
4082
4083    public static short[] doubleArrayToSafeShortArray(double[] array, boolean signed)
4084    {
4085        return doubleArrayToSafeShortArray(array, 0, null, 0, array.length, signed);
4086    }
4087
4088    public static byte[] doubleArrayToSafeByteArray(double[] array, boolean signed)
4089    {
4090        return doubleArrayToSafeByteArray(array, 0, null, 0, array.length, signed);
4091    }
4092
4093    public static long[] floatArrayToSafeLongArray(float[] array, boolean signed)
4094    {
4095        return floatArrayToSafeLongArray(array, 0, null, 0, array.length, signed);
4096    }
4097
4098    public static int[] floatArrayToSafeIntArray(float[] array, boolean signed)
4099    {
4100        return floatArrayToSafeIntArray(array, 0, null, 0, array.length, signed);
4101    }
4102
4103    public static short[] floatArrayToSafeShortArray(float[] array, boolean signed)
4104    {
4105        return floatArrayToSafeShortArray(array, 0, null, 0, array.length, signed);
4106    }
4107
4108    public static byte[] floatArrayToSafeByteArray(float[] array, boolean signed)
4109    {
4110        return floatArrayToSafeByteArray(array, 0, null, 0, array.length, signed);
4111    }
4112
4113    public static int[] longArrayToSafeIntArray(long[] array, boolean signed)
4114    {
4115        return longArrayToSafeIntArray(array, 0, null, 0, array.length, signed, signed);
4116    }
4117
4118    public static short[] longArrayToSafeShortArray(long[] array, boolean signed)
4119    {
4120        return longArrayToSafeShortArray(array, 0, null, 0, array.length, signed, signed);
4121    }
4122
4123    public static byte[] longArrayToSafeByteArray(long[] array, boolean signed)
4124    {
4125        return longArrayToSafeByteArray(array, 0, null, 0, array.length, signed, signed);
4126    }
4127
4128    public static short[] intArrayToSafeShortArray(int[] array, boolean signed)
4129    {
4130        return intArrayToSafeShortArray(array, 0, null, 0, array.length, signed, signed);
4131    }
4132
4133    public static byte[] intArrayToSafeByteArray(int[] array, boolean signed)
4134    {
4135        return intArrayToSafeByteArray(array, 0, null, 0, array.length, signed, signed);
4136    }
4137
4138    public static byte[] shortArrayToSafeByteArray(short[] array, boolean signed)
4139    {
4140        return shortArrayToSafeByteArray(array, 0, null, 0, array.length, signed, signed);
4141    }
4142
4143    //
4144    //
4145    //
4146    //
4147
4148    /**
4149     * Return the specified 1D array as string<br>
4150     * Default representation use ':' as separator character<br>
4151     * <br>
4152     * ex : [0,1,2,3,4] --> "0:1:2:3:4"<br>
4153     * 
4154     * @param array
4155     *        1D array containing values to return as string
4156     */
4157    public static String arrayToString(Object array)
4158    {
4159        return arrayToString(array, false, false, ":", -1);
4160    }
4161
4162    /**
4163     * Return the specified 1D array as string<br>
4164     * ex : [0,1,2,3,4] --> "0:1:2:3:4"<br>
4165     * ex : [Obj0,Obj1,Obj2,Obj3,Obj4] --> "Obj0:Obj1:Obj2:Obj3:Obj4"<br>
4166     * 
4167     * @param array
4168     *        1D array containing values to return as string
4169     * @param signed
4170     *        input value are signed (only for integer data type)
4171     * @param hexa
4172     *        set value in resulting string in hexa decimal format (only for integer data type)
4173     * @param separator
4174     *        specify the separator to use between each array value in resulting string
4175     * @param size
4176     *        specify the number of significant number to display for float value (-1 means all)
4177     */
4178    public static String arrayToString(Object array, boolean signed, boolean hexa, String separator, int size)
4179    {
4180        final int len = ArrayUtil.getLength(array);
4181        final DataType dataType = ArrayUtil.getDataType(array, signed);
4182        final StringBuilder result = new StringBuilder();
4183        final int base = hexa ? 16 : 10;
4184
4185        switch (dataType)
4186        {
4187            case UBYTE:
4188            {
4189                final byte[] data = (byte[]) array;
4190
4191                if (len > 0)
4192                    result.append(Integer.toString(data[0] & 0xFF, base));
4193                for (int i = 1; i < len; i++)
4194                {
4195                    result.append(separator);
4196                    result.append(Integer.toString(data[i] & 0xFF, base));
4197                }
4198                break;
4199            }
4200
4201            case BYTE:
4202            {
4203                final byte[] data = (byte[]) array;
4204
4205                if (len > 0)
4206                    result.append(Integer.toString(data[0], base));
4207                for (int i = 1; i < len; i++)
4208                {
4209                    result.append(separator);
4210                    result.append(Integer.toString(data[i], base));
4211                }
4212                break;
4213            }
4214
4215            case USHORT:
4216            {
4217                final short[] data = (short[]) array;
4218
4219                if (len > 0)
4220                    result.append(Integer.toString(data[0] & 0xFFFF, base));
4221                for (int i = 1; i < len; i++)
4222                {
4223                    result.append(separator);
4224                    result.append(Integer.toString(data[i] & 0xFFFF, base));
4225                }
4226                break;
4227            }
4228            case SHORT:
4229            {
4230                final short[] data = (short[]) array;
4231
4232                if (len > 0)
4233                    result.append(Integer.toString(data[0], base));
4234                for (int i = 1; i < len; i++)
4235                {
4236                    result.append(separator);
4237                    result.append(Integer.toString(data[i], base));
4238                }
4239                break;
4240            }
4241
4242            case UINT:
4243            {
4244                final int[] data = (int[]) array;
4245
4246                if (len > 0)
4247                    result.append(Long.toString(data[0] & 0xFFFFFFFFL, base));
4248                for (int i = 1; i < len; i++)
4249                {
4250                    result.append(separator);
4251                    result.append(Long.toString(data[i] & 0xFFFFFFFFL, base));
4252                }
4253                break;
4254            }
4255
4256            case INT:
4257            {
4258                final int[] data = (int[]) array;
4259
4260                if (len > 0)
4261                    result.append(Integer.toString(data[0], base));
4262                for (int i = 1; i < len; i++)
4263                {
4264                    result.append(separator);
4265                    result.append(Integer.toString(data[i], base));
4266                }
4267                break;
4268            }
4269
4270            case ULONG:
4271            {
4272                final long[] data = (long[]) array;
4273
4274                // we lost highest bit as java doesn't have bigger than long type
4275                if (len > 0)
4276                    result.append(Long.toString(data[0] & 0x7FFFFFFFFFFFFFFFL, base));
4277                for (int i = 1; i < len; i++)
4278                {
4279                    result.append(separator);
4280                    result.append(Long.toString(data[i] & 0x7FFFFFFFFFFFFFFFL, base));
4281                }
4282                break;
4283            }
4284
4285            case LONG:
4286            {
4287                final long[] data = (long[]) array;
4288
4289                if (len > 0)
4290                    result.append(Long.toString(data[0], base));
4291                for (int i = 1; i < len; i++)
4292                {
4293                    result.append(separator);
4294                    result.append(Long.toString(data[i], base));
4295                }
4296                break;
4297            }
4298
4299            case FLOAT:
4300            {
4301                final float[] data = (float[]) array;
4302
4303                if (size == -1)
4304                {
4305                    if (len > 0)
4306                        result.append(data[0]);
4307                    for (int i = 1; i < len; i++)
4308                    {
4309                        result.append(separator);
4310                        result.append(data[i]);
4311                    }
4312                }
4313                else
4314                {
4315                    if (len > 0)
4316                        result.append(Double.toString(MathUtil.roundSignificant(data[0], size, true)));
4317                    for (int i = 1; i < len; i++)
4318                    {
4319                        result.append(separator);
4320                        result.append(Double.toString(MathUtil.roundSignificant(data[i], size, true)));
4321                    }
4322                }
4323                break;
4324            }
4325
4326            case DOUBLE:
4327            {
4328                final double[] data = (double[]) array;
4329
4330                if (size == -1)
4331                {
4332                    if (len > 0)
4333                        result.append(data[0]);
4334                    for (int i = 1; i < len; i++)
4335                    {
4336                        result.append(separator);
4337                        result.append(data[i]);
4338                    }
4339                }
4340                else
4341                {
4342                    if (len > 0)
4343                        result.append(Double.toString(MathUtil.roundSignificant(data[0], size, true)));
4344                    for (int i = 1; i < len; i++)
4345                    {
4346                        result.append(separator);
4347                        result.append(Double.toString(MathUtil.roundSignificant(data[i], size, true)));
4348                    }
4349                }
4350                break;
4351            }
4352
4353            // generic method
4354            default:
4355            {
4356                if (len > 0)
4357                    result.append(Array.get(array, 0).toString());
4358                for (int i = 1; i < len; i++)
4359                {
4360                    result.append(separator);
4361                    result.append(Array.get(array, i).toString());
4362                }
4363            }
4364        }
4365
4366        return result.toString();
4367    }
4368
4369    /**
4370     * Return the specified string containing separated values as a 1D array<br>
4371     * By default separator is assumed to be ':' character<br>
4372     * ex : "0:1:2:3:4" --> [0,1,2,3,4]<br>
4373     * 
4374     * @param value
4375     *        string containing value to return as 1D array
4376     * @param dataType
4377     *        specify the values data type and also the output array data type string
4378     */
4379    public static Object stringToArray(String value, DataType dataType)
4380    {
4381        return stringToArray(value, dataType, false, ":");
4382    }
4383
4384    /**
4385     * @deprecated use {@link #stringToArray(String, DataType)} instead
4386     */
4387    @Deprecated
4388    public static Object stringToArray(String value, int dataType)
4389    {
4390        return stringToArray(value, DataType.getDataType(dataType), false, ":");
4391    }
4392
4393    /**
4394     * Return the specified string containing separated values as a 1D array<br>
4395     * ex : "0:1:2:3:4" --> [0,1,2,3,4]<br>
4396     * 
4397     * @param value
4398     *        string containing value to return as 1D array
4399     * @param dataType
4400     *        specify the values data type and also the output array data type string
4401     * @param hexa
4402     *        values in string as stored as hexa values (only for integer data type)
4403     * @param separator
4404     *        specify the separator used between each value in the input string
4405     */
4406    public static Object stringToArray(String value, DataType dataType, boolean hexa, String separator)
4407    {
4408        if (StringUtil.isEmpty(value))
4409            return createArray(dataType, 0);
4410
4411        final String[] values = value.split(separator);
4412        final int len = values.length;
4413        final int base = hexa ? 16 : 10;
4414
4415        switch (dataType.getJavaType())
4416        {
4417            case BYTE:
4418            {
4419                final byte[] result = new byte[len];
4420
4421                for (int i = 0; i < len; i++)
4422                    result[i] = (byte) Integer.parseInt(values[i], base);
4423
4424                return result;
4425            }
4426
4427            case SHORT:
4428            {
4429                final short[] result = new short[len];
4430
4431                for (int i = 0; i < len; i++)
4432                    result[i] = (short) Integer.parseInt(values[i], base);
4433
4434                return result;
4435            }
4436
4437            case INT:
4438            {
4439                final int[] result = new int[len];
4440
4441                for (int i = 0; i < len; i++)
4442                    result[i] = Integer.parseInt(values[i], base);
4443
4444                return result;
4445            }
4446
4447            case LONG:
4448            {
4449                final long[] result = new long[len];
4450
4451                for (int i = 0; i < len; i++)
4452                    result[i] = Long.parseLong(values[i], base);
4453
4454                return result;
4455            }
4456
4457            case FLOAT:
4458            {
4459                final float[] result = new float[len];
4460
4461                for (int i = 0; i < len; i++)
4462                    result[i] = Float.parseFloat(values[i]);
4463
4464                return result;
4465            }
4466
4467            case DOUBLE:
4468            {
4469                final double[] result = new double[len];
4470
4471                for (int i = 0; i < len; i++)
4472                    result[i] = Double.parseDouble(values[i]);
4473
4474                return result;
4475            }
4476        }
4477
4478        return null;
4479    }
4480
4481    /**
4482     * @deprecated use {@link #stringToArray(String, DataType, boolean, String)} instead
4483     */
4484    @Deprecated
4485    public static Object stringToArray(String value, int dataType, boolean hexa, String separator)
4486    {
4487        return stringToArray(value, DataType.getDataType(dataType, false), hexa, separator);
4488    }
4489
4490    //
4491    //
4492    //
4493    //
4494
4495    /**
4496     * Convert a boolean array to a byte array (unpacked form : 1 boolean --> 1 byte)
4497     */
4498    public static byte[] toByteArray(boolean[] array)
4499    {
4500        return toByteArray(array, null, 0);
4501    }
4502
4503    /**
4504     * Convert a boolean array to a byte array (unpacked form : 1 boolean --> 1 byte)
4505     * The resulting array is returned in 'out' and from the specified if any.<br>
4506     * If (out == null) a new array is allocated.
4507     */
4508    public static byte[] toByteArray(boolean[] in, byte[] out, int offset)
4509    {
4510        if (in == null)
4511            return new byte[0];
4512
4513        final int len = in.length;
4514        final byte[] result = allocIfNull(out, offset + len);
4515
4516        for (int i = 0; i < len; i++)
4517            result[i] = (byte) ((in[i]) ? 1 : 0);
4518
4519        return result;
4520    }
4521
4522    /**
4523     * Convert a byte array (unpacked form : 1 byte --> 1 boolean) to a boolean array
4524     */
4525    public static boolean[] toBooleanArray(byte[] array)
4526    {
4527        return toBooleanArray(array, null, 0);
4528    }
4529
4530    /**
4531     * Convert a boolean array to a byte array (unpacked form : 1 boolean --> 1 byte)
4532     * The resulting array is returned in 'out' and from the specified if any.<br>
4533     * If (out == null) a new array is allocated.
4534     */
4535    public static boolean[] toBooleanArray(byte[] in, boolean[] out, int offset)
4536    {
4537        if (in == null)
4538            return new boolean[0];
4539
4540        final int len = in.length;
4541        final boolean[] result = allocIfNull(out, offset + len);
4542
4543        for (int i = 0; i < len; i++)
4544            result[i] = (in[i] != 0) ? true : false;
4545
4546        return result;
4547    }
4548
4549    /**
4550     * Retrieve interleaved byte data from 'in' array and return the result in the 'out' array.
4551     * 
4552     * @param in
4553     *        input byte array containing interleaved data
4554     * @param inOffset
4555     *        input array offset
4556     * @param step
4557     *        interleave step
4558     * @param out
4559     *        output result array. If set to <code>null</code> then a new array is allocated.
4560     * @param outOffset
4561     *        output array offset
4562     * @param size
4563     *        number of byte to retrieve
4564     * @return byte array containing de-interleaved data.
4565     */
4566    public static byte[] getInterleavedData(byte[] in, int inOffset, int step, byte[] out, int outOffset, int size)
4567    {
4568        final byte[] result = allocIfNull(out, outOffset + size);
4569
4570        int inOff = inOffset;
4571        int outOff = outOffset;
4572
4573        for (int i = 0; i < size; i++)
4574        {
4575            result[outOff] = in[inOff];
4576            inOff += step;
4577            outOff++;
4578        }
4579
4580        return result;
4581    }
4582
4583    /**
4584     * De interleave data from 'in' array and return the result in the 'out' array.
4585     * 
4586     * @param in
4587     *        input byte array containing interleaved data
4588     * @param inOffset
4589     *        input array offset
4590     * @param step
4591     *        interleave step
4592     * @param out
4593     *        output result array. If set to <code>null</code> then a new array is allocated
4594     * @param outOffset
4595     *        output array offset
4596     * @param size
4597     *        number of element to de-interleave
4598     * @return byte array containing de-interleaved data.
4599     */
4600    public static byte[] deInterleave(byte[] in, int inOffset, int step, byte[] out, int outOffset, int size)
4601    {
4602        final byte[] result = allocIfNull(out, outOffset + (size * step));
4603
4604        int inOff1 = inOffset;
4605        int outOff1 = outOffset;
4606
4607        for (int j = 0; j < step; j++)
4608        {
4609            int inOff2 = inOff1;
4610            int outOff2 = outOff1;
4611
4612            for (int i = 0; i < size; i++)
4613            {
4614                result[outOff2] = in[inOff2];
4615                inOff2 += step;
4616                outOff2++;
4617            }
4618
4619            inOff1++;
4620            outOff1 += size;
4621        }
4622
4623        return result;
4624    }
4625}