001/*-
002 *******************************************************************************
003 * Copyright (c) 2011, 2016 Diamond Light Source Ltd.
004 * All rights reserved. This program and the accompanying materials
005 * are made available under the terms of the Eclipse Public License v1.0
006 * which accompanies this distribution, and is available at
007 * http://www.eclipse.org/legal/epl-v10.html
008 *
009 * Contributors:
010 *    Peter Chang - initial API and implementation and/or initial documentation
011 *******************************************************************************/
012
013// This is generated from DoubleDataset.java by fromdouble.py
014
015package org.eclipse.january.dataset;
016
017import java.util.ArrayList;
018import java.util.Arrays;
019import java.util.List;
020import java.util.Set;
021import java.util.TreeSet;
022
023import org.apache.commons.math3.complex.Complex;
024import org.eclipse.january.metadata.StatisticsMetadata;
025
026
027/**
028 * Extend dataset for float values // PRIM_TYPE
029 */
030public class FloatDataset extends AbstractDataset {
031        // pin UID to base class
032        private static final long serialVersionUID = Dataset.serialVersionUID;
033
034        protected float[] data; // subclass alias // PRIM_TYPE
035
036        @Override
037        protected void setData() {
038                data = (float[]) odata; // PRIM_TYPE
039        }
040
041        protected static float[] createArray(final int size) { // PRIM_TYPE
042                float[] array = null; // PRIM_TYPE
043
044                try {
045                        array = new float[size]; // PRIM_TYPE
046                } catch (OutOfMemoryError e) {
047                        logger.error("The size of the dataset ({}) that is being created is too large "
048                                        + "and there is not enough memory to hold it.", size);
049                        throw new OutOfMemoryError("The dimensions given are too large, and there is "
050                                        + "not enough memory available in the Java Virtual Machine");
051                }
052                return array;
053        }
054
055        @Override
056        public int getDType() {
057                return FLOAT32; // DATA_TYPE
058        }
059
060        /**
061         * Create a null dataset
062         */
063        FloatDataset() {
064        }
065
066        /**
067         * Create a zero-filled dataset of given shape
068         * @param shape
069         */
070        FloatDataset(final int... shape) {
071                if (shape != null) {
072                        size = ShapeUtils.calcSize(shape);
073                        this.shape = shape.clone();
074
075                        try {
076                                odata = data = createArray(size);
077                        } catch (Throwable t) {
078                                logger.error("Could not create a dataset of shape {}", Arrays.toString(shape), t);
079                                throw new IllegalArgumentException(t);
080                        }
081                }
082        }
083
084        /**
085         * Create a dataset using given data
086         * @param data
087         * @param shape
088         *            (can be null to create 1D dataset)
089         */
090        FloatDataset(final float[] data, int... shape) { // PRIM_TYPE
091                if (data == null) {
092                        throw new IllegalArgumentException("Data must not be null");
093                }
094                if (shape == null || shape.length == 0) {
095                        shape = new int[] { data.length };
096                }
097                size = ShapeUtils.calcSize(shape);
098                if (size != data.length) {
099                        throw new IllegalArgumentException(String.format("Shape %s is not compatible with size of data array, %d",
100                                        Arrays.toString(shape), data.length));
101                }
102                this.shape = size == 0 ? null : shape.clone();
103
104                odata = this.data = data;
105        }
106
107        /**
108         * Copy a dataset
109         * @param dataset
110         */
111        FloatDataset(final FloatDataset dataset) {
112                copyToView(dataset, this, true, true);
113
114                try {
115                        if (dataset.stride == null) {
116                                odata = data = dataset.data.clone();
117                        } else {
118                                offset = 0;
119                                stride = null;
120                                base = null;
121                                odata = data = createArray(size);
122
123                                IndexIterator iter = dataset.getIterator();
124                                for (int i = 0; iter.hasNext(); i++) {
125                                        data[i] = dataset.data[iter.index];
126                                }
127                        }
128                } catch (Throwable t) {
129                        logger.error("Could not create a dataset of shape {}", Arrays.toString(shape), t);
130                        throw new IllegalArgumentException(t);
131                }
132        }
133
134        /**
135         * Copy and cast a dataset to this class type
136         * @param dataset
137         */
138        FloatDataset(final Dataset dataset) {
139                copyToView(dataset, this, true, false);
140                offset = 0;
141                stride = null;
142                base = null;
143                try {
144                        odata = data = createArray(size);
145                } catch (Throwable t) {
146                        logger.error("Could not create a dataset of shape {}", Arrays.toString(shape), t);
147                        throw new IllegalArgumentException(t);
148                }
149                IndexIterator iter = dataset.getIterator();
150                for (int i = 0; iter.hasNext(); i++) {
151                        data[i] = (float) dataset.getElementDoubleAbs(iter.index); // GET_ELEMENT_WITH_CAST
152                }
153        }
154
155        @Override
156        public boolean equals(Object obj) {
157                if (!super.equals(obj)) {
158                        return false;
159                }
160
161                if (getRank() == 0 && !getClass().equals(obj.getClass())) // already true for zero-rank dataset
162                        return true;
163
164                FloatDataset other = (FloatDataset) obj;
165//              if (size == 1) // for zero-rank datasets
166//                      return getAbs(offset) == other.getAbs(other.offset);
167
168                IndexIterator iter = getIterator();
169                IndexIterator oiter = other.getIterator();
170                while (iter.hasNext() && oiter.hasNext()) {
171                        if (data[iter.index] != other.data[oiter.index]) // OBJECT_UNEQUAL
172                                return false;
173                }
174                return true;
175        }
176
177        @Override
178        public int hashCode() {
179                return super.hashCode();
180        }
181
182        @Override
183        public FloatDataset clone() {
184                return new FloatDataset(this);
185        }
186
187        /**
188         * Create a dataset from an object which could be a Java list, array (of arrays...) or Number. Ragged
189         * sequences or arrays are padded with zeros.
190         *
191         * @param obj
192         * @return dataset with contents given by input
193         */
194        static FloatDataset createFromObject(final Object obj) {
195                FloatDataset result = new FloatDataset();
196
197                if (obj != null) {
198                        result.shape = ShapeUtils.getShapeFromObject(obj);
199                        result.size = ShapeUtils.calcSize(result.shape);
200
201                        try {
202                                result.odata = result.data = createArray(result.size);
203                        } catch (Throwable t) {
204                                logger.error("Could not create a dataset of shape {}", Arrays.toString(result.shape), t);
205                                throw new IllegalArgumentException(t);
206                        }
207
208                        int[] pos = new int[result.shape.length];
209                        result.fillData(obj, 0, pos);
210                }
211
212                return result;
213        }
214        
215        /**
216         *
217         * @param stop
218         * @return a new 1D dataset, filled with values determined by parameters
219         */
220        static FloatDataset createRange(final double stop) {
221                return createRange(0, stop, 1);
222        }
223        
224        /**
225         *
226         * @param start
227         * @param stop
228         * @param step
229         * @return a new 1D dataset, filled with values determined by parameters
230         */
231        static FloatDataset createRange(final double start, final double stop, final double step) {
232                int size = calcSteps(start, stop, step);
233                FloatDataset result = new FloatDataset(size);
234                for (int i = 0; i < size; i++) {
235                        result.data[i] = (float) (start + i * step); // PRIM_TYPE // ADD_CAST
236                }
237                return result;
238        }
239
240        /**
241         * @param shape
242         * @return a dataset filled with ones
243         */
244        static FloatDataset ones(final int... shape) {
245                return new FloatDataset(shape).fill(1);
246        }
247
248        @Override
249        public FloatDataset fill(final Object obj) {
250                setDirty();
251                float dv = (float) DTypeUtils.toReal(obj); // PRIM_TYPE // FROM_OBJECT
252                IndexIterator iter = getIterator();
253                while (iter.hasNext()) {
254                        data[iter.index] = dv;
255                }
256
257                return this;
258        }
259
260        /**
261         * This is a typed version of {@link #getBuffer()}
262         * @return data buffer as linear array
263         */
264        public float[] getData() { // PRIM_TYPE
265                return data;
266        }
267
268        @Override
269        protected int getBufferLength() {
270                if (data == null)
271                        return 0;
272                return data.length;
273        }
274
275        @Override
276        public FloatDataset getView(boolean deepCopyMetadata) {
277                FloatDataset view = new FloatDataset();
278                copyToView(this, view, true, deepCopyMetadata);
279                view.setData();
280                return view;
281        }
282
283        /**
284         * Get a value from an absolute index of the internal array. This is an internal method with no checks so can be
285         * dangerous. Use with care or ideally with an iterator.
286         *
287         * @param index
288         *            absolute index
289         * @return value
290         */
291        public float getAbs(final int index) { // PRIM_TYPE
292                return data[index];
293        }
294
295        @Override
296        public boolean getElementBooleanAbs(final int index) {
297                return data[index] != 0; // BOOLEAN_FALSE
298        }
299
300        @Override
301        public double getElementDoubleAbs(final int index) {
302                return data[index]; // BOOLEAN_ZERO
303        }
304
305        @Override
306        public long getElementLongAbs(final int index) {
307                return (long) data[index]; // BOOLEAN_ZERO // OMIT_CAST_INT
308        }
309
310        @Override
311        public Object getObjectAbs(final int index) {
312                return data[index];
313        }
314
315        @Override
316        public String getStringAbs(final int index) {
317                return stringFormat == null ? String.format("%.8g", data[index]) : // FORMAT_STRING
318                        stringFormat.format(data[index]);
319        }
320
321        /**
322         * Set a value at absolute index in the internal array. This is an internal method with no checks so can be
323         * dangerous. Use with care or ideally with an iterator.
324         *
325         * @param index
326         *            absolute index
327         * @param val
328         *            new value
329         */
330        public void setAbs(final int index, final float val) { // PRIM_TYPE
331                setDirty();
332                data[index] = val;
333        }
334
335        @Override
336        protected void setItemDirect(final int dindex, final int sindex, final Object src) {
337                setDirty();
338                float[] dsrc = (float[]) src; // PRIM_TYPE
339                data[dindex] = dsrc[sindex];
340        }
341
342        @Override
343        public void setObjectAbs(final int index, final Object obj) {
344                if (index < 0 || index > data.length) {
345                        throw new IndexOutOfBoundsException("Index given is outside dataset");
346                }
347
348                setAbs(index, (float) DTypeUtils.toReal(obj)); // FROM_OBJECT
349        }
350
351        /**
352         * @return item in first position
353         * @since 2.0
354         */
355        public float get() { // PRIM_TYPE
356                return data[getFirst1DIndex()];
357        }
358
359        /**
360         * @param i
361         * @return item in given position
362         */
363        public float get(final int i) { // PRIM_TYPE
364                return data[get1DIndex(i)];
365        }
366
367        /**
368         * @param i
369         * @param j
370         * @return item in given position
371         */
372        public float get(final int i, final int j) { // PRIM_TYPE
373                return data[get1DIndex(i, j)];
374        }
375
376        /**
377         * @param pos
378         * @return item in given position
379         */
380        public float get(final int... pos) { // PRIM_TYPE
381                return data[get1DIndex(pos)];
382        }
383
384        @Override
385        public Object getObject() {
386                return Float.valueOf(get()); // CLASS_TYPE
387        }
388
389        @Override
390        public Object getObject(final int i) {
391                return Float.valueOf(get(i)); // CLASS_TYPE
392        }
393
394        @Override
395        public Object getObject(final int i, final int j) {
396                return Float.valueOf(get(i, j)); // CLASS_TYPE
397        }
398
399        @Override
400        public Object getObject(final int... pos) {
401                return Float.valueOf(get(pos)); // CLASS_TYPE
402        }
403
404        @Override
405        public String getString() {
406                return getStringAbs(getFirst1DIndex());
407        }
408
409        @Override
410        public String getString(final int i) {
411                return getStringAbs(get1DIndex(i));
412        }
413
414        @Override
415        public String getString(final int i, final int j) {
416                return getStringAbs(get1DIndex(i, j));
417        }
418
419        @Override
420        public String getString(final int... pos) {
421                return getStringAbs(get1DIndex(pos));
422        }
423
424        @Override
425        public double getDouble() {
426                return get(); // BOOLEAN_ZERO
427        }
428
429        @Override
430        public double getDouble(final int i) {
431                return get(i); // BOOLEAN_ZERO
432        }
433
434        @Override
435        public double getDouble(final int i, final int j) {
436                return get(i, j); // BOOLEAN_ZERO
437        }
438
439        @Override
440        public double getDouble(final int... pos) {
441                return get(pos); // BOOLEAN_ZERO
442        }
443
444        @Override
445        public float getFloat() {
446                return get(); // BOOLEAN_ZERO // OMIT_REAL_CAST
447        }
448
449        @Override
450        public float getFloat(final int i) {
451                return get(i); // BOOLEAN_ZERO // OMIT_REAL_CAST
452        }
453
454        @Override
455        public float getFloat(final int i, final int j) {
456                return get(i, j); // BOOLEAN_ZERO // OMIT_REAL_CAST
457        }
458
459        @Override
460        public float getFloat(final int... pos) {
461                return get(pos); // BOOLEAN_ZERO // OMIT_REAL_CAST
462        }
463
464        @Override
465        public long getLong() {
466                return (long) get(); // BOOLEAN_ZERO // OMIT_UPCAST
467        }
468
469        @Override
470        public long getLong(final int i) {
471                return (long) get(i); // BOOLEAN_ZERO // OMIT_UPCAST
472        }
473
474        @Override
475        public long getLong(final int i, final int j) {
476                return (long) get(i, j); // BOOLEAN_ZERO // OMIT_UPCAST
477        }
478
479        @Override
480        public long getLong(final int... pos) {
481                return (long) get(pos); // BOOLEAN_ZERO // OMIT_UPCAST
482        }
483
484        @Override
485        public int getInt() {
486                return (int) get(); // BOOLEAN_ZERO // OMIT_UPCAST
487        }
488
489        @Override
490        public int getInt(final int i) {
491                return (int) get(i); // BOOLEAN_ZERO // OMIT_UPCAST
492        }
493
494        @Override
495        public int getInt(final int i, final int j) {
496                return (int) get(i, j); // BOOLEAN_ZERO // OMIT_UPCAST
497        }
498
499        @Override
500        public int getInt(final int... pos) {
501                return (int) get(pos); // BOOLEAN_ZERO // OMIT_UPCAST
502        }
503
504        @Override
505        public short getShort() {
506                return (short) get(); // BOOLEAN_ZERO // OMIT_UPCAST
507        }
508
509        @Override
510        public short getShort(final int i) {
511                return (short) get(i); // BOOLEAN_ZERO // OMIT_UPCAST
512        }
513
514        @Override
515        public short getShort(final int i, final int j) {
516                return (short) get(i, j); // BOOLEAN_ZERO // OMIT_UPCAST
517        }
518
519        @Override
520        public short getShort(final int... pos) {
521                return (short) get(pos); // BOOLEAN_ZERO // OMIT_UPCAST
522        }
523
524        @Override
525        public byte getByte() {
526                return (byte) get(); // BOOLEAN_ZERO // OMIT_UPCAST
527        }
528
529        @Override
530        public byte getByte(final int i) {
531                return (byte) get(i); // BOOLEAN_ZERO // OMIT_UPCAST
532        }
533
534        @Override
535        public byte getByte(final int i, final int j) {
536                return (byte) get(i, j); // BOOLEAN_ZERO // OMIT_UPCAST
537        }
538
539        @Override
540        public byte getByte(final int... pos) {
541                return (byte) get(pos); // BOOLEAN_ZERO // OMIT_UPCAST
542        }
543
544        @Override
545        public boolean getBoolean() {
546                return get() != 0; // BOOLEAN_FALSE
547        }
548
549        @Override
550        public boolean getBoolean(final int i) {
551                return get(i) != 0; // BOOLEAN_FALSE
552        }
553
554        @Override
555        public boolean getBoolean(final int i, final int j) {
556                return get(i, j) != 0; // BOOLEAN_FALSE
557        }
558
559        @Override
560        public boolean getBoolean(final int... pos) {
561                return get(pos) != 0; // BOOLEAN_FALSE
562        }
563
564        /**
565         * Sets the value at first point to the passed value. The dataset must not be null
566         *
567         * @param value
568         * @since 2.0
569         */
570        public void setItem(final float value) { // PRIM_TYPE
571                setAbs(getFirst1DIndex(), value);
572        }
573
574        /**
575         * Sets the value at a particular point to the passed value. The dataset must be 1D
576         *
577         * @param value
578         * @param i
579         */
580        public void setItem(final float value, final int i) { // PRIM_TYPE
581                setAbs(get1DIndex(i), value);
582        }
583
584        /**
585         * Sets the value at a particular point to the passed value. The dataset must be 2D
586         *
587         * @param value
588         * @param i
589         * @param j
590         */
591        public void setItem(final float value, final int i, final int j) { // PRIM_TYPE
592                setAbs(get1DIndex(i, j), value);
593        }
594
595        /**
596         * Sets the value at a particular point to the passed value
597         *
598         * @param value
599         * @param pos
600         */
601        public void setItem(final float value, final int... pos) { // PRIM_TYPE
602                setAbs(get1DIndex(pos), value);
603        }
604
605        @Override
606        public void set(final Object obj) {
607                setItem((float) DTypeUtils.toReal(obj)); // FROM_OBJECT
608        }
609
610        @Override
611        public void set(final Object obj, final int i) {
612                setItem((float) DTypeUtils.toReal(obj), i); // FROM_OBJECT
613        }
614
615        @Override
616        public void set(final Object obj, final int i, final int j) {
617                setItem((float) DTypeUtils.toReal(obj), i, j); // FROM_OBJECT
618        }
619
620        @Override
621        public void set(final Object obj, int... pos) {
622                if (pos == null || (pos.length == 0 && shape.length > 0)) {
623                        pos = new int[shape.length];
624                }
625
626                setItem((float) DTypeUtils.toReal(obj), pos); // FROM_OBJECT
627        }
628
629
630        @Override
631        public void resize(int... newShape) {
632                setDirty();
633                final IndexIterator iter = getIterator();
634                final int nsize = ShapeUtils.calcSize(newShape);
635                final float[] ndata; // PRIM_TYPE
636                try {
637                        ndata = createArray(nsize);
638                } catch (Throwable t) {
639                        logger.error("Could not create a dataset of shape {}", Arrays.toString(shape), t);
640                        throw new IllegalArgumentException(t);
641                }
642                for (int i = 0; iter.hasNext() && i < nsize; i++) {
643                        ndata[i] = data[iter.index];
644                }
645
646                odata = data = ndata;
647                size = nsize;
648                shape = newShape;
649                stride = null;
650                offset = 0;
651                base = null;
652        }
653
654        @Override
655        public FloatDataset sort(Integer axis) {
656                setDirty();
657                if (axis == null) {
658                        if (stride == null) {
659                                Arrays.sort(data);
660                        } else {
661                                FloatDataset ads = clone().sort(null);
662                                setSlicedView(getView(false), ads);
663                        }
664                } else {
665                        axis = checkAxis(axis);
666                        
667                        FloatDataset ads = new FloatDataset(shape[axis]);
668                        PositionIterator pi = getPositionIterator(axis);
669                        int[] pos = pi.getPos();
670                        boolean[] hit = pi.getOmit();
671                        while (pi.hasNext()) {
672                                copyItemsFromAxes(pos, hit, ads);
673                                Arrays.sort(ads.data);
674                                setItemsOnAxes(pos, hit, ads.data);
675                        }
676                }
677                return this;
678                // throw new UnsupportedOperationException("Cannot sort dataset"); // BOOLEAN_USE
679        }
680
681        @Override
682        public FloatDataset getUniqueItems() {
683                Set<Float> set = new TreeSet<Float>(); // CLASS_TYPE
684                IndexIterator it = getIterator();
685                while (it.hasNext()) {
686                        set.add(data[it.index]);
687                }
688
689                FloatDataset u = new FloatDataset(set.size()); // CLASS_TYPE
690                int i = 0;
691                float[] udata = u.getData(); // PRIM_TYPE
692                for (Float v : set) { // CLASS_TYPE
693                        udata[i++] = v;
694                }
695                return u;
696        }
697
698        @Override
699        public FloatDataset getSlice(final SliceIterator siter) {
700                FloatDataset result = new FloatDataset(siter.getShape());
701                float[] rdata = result.data; // PRIM_TYPE
702
703                for (int i = 0; siter.hasNext(); i++)
704                        rdata[i] = data[siter.index];
705
706                result.setName(name + BLOCK_OPEN + Slice.createString(siter.shape, siter.start, siter.stop, siter.step) + BLOCK_CLOSE);
707                return result;
708        }
709
710        @Override
711        public void fillDataset(Dataset result, IndexIterator iter) {
712                setDirty();
713                IndexIterator riter = result.getIterator();
714
715                float[] rdata = ((FloatDataset) result).data; // PRIM_TYPE
716
717                while (riter.hasNext() && iter.hasNext()) {
718                        rdata[riter.index] = data[iter.index];
719                }
720        }
721
722        @Override
723        public FloatDataset setByBoolean(final Object obj, Dataset selection) {
724                setDirty();
725                if (obj instanceof Dataset) {
726                        final Dataset ds = (Dataset) obj;
727                        final int length = ((Number) selection.sum()).intValue();
728                        if (length != ds.getSize()) {
729                                throw new IllegalArgumentException(
730                                                "Number of true items in selection does not match number of items in dataset");
731                        }
732
733                        final IndexIterator oiter = ds.getIterator();
734                        final BooleanIterator biter = getBooleanIterator(selection);
735
736                        while (biter.hasNext() && oiter.hasNext()) {
737                                data[biter.index] = (float) ds.getElementDoubleAbs(oiter.index); // GET_ELEMENT_WITH_CAST
738                        }
739                } else {
740                        final float dv = (float) DTypeUtils.toReal(obj); // PRIM_TYPE // FROM_OBJECT
741                        final BooleanIterator biter = getBooleanIterator(selection);
742
743                        while (biter.hasNext()) {
744                                data[biter.index] = dv;
745                        }
746                }
747                return this;
748        }
749
750        @Override
751        public FloatDataset setBy1DIndex(final Object obj, final Dataset index) {
752                setDirty();
753                if (obj instanceof Dataset) {
754                        final Dataset ds = (Dataset) obj;
755                        if (index.getSize() != ds.getSize()) {
756                                throw new IllegalArgumentException(
757                                                "Number of items in index dataset does not match number of items in dataset");
758                        }
759
760                        final IndexIterator oiter = ds.getIterator();
761                        final IntegerIterator iter = new IntegerIterator(index, size);
762
763                        while (iter.hasNext() && oiter.hasNext()) {
764                                data[iter.index] = (float) ds.getElementDoubleAbs(oiter.index); // GET_ELEMENT_WITH_CAST
765                        }
766                } else {
767                        final float dv = (float) DTypeUtils.toReal(obj); // PRIM_TYPE // FROM_OBJECT
768                        IntegerIterator iter = new IntegerIterator(index, size);
769
770                        while (iter.hasNext()) {
771                                data[iter.index] = dv;
772                        }
773                }
774                return this;
775        }
776
777        @Override
778        public FloatDataset setByIndexes(final Object obj, final Object... indexes) {
779                setDirty();
780                final IntegersIterator iter = new IntegersIterator(shape, indexes);
781                final int[] pos = iter.getPos();
782
783                if (obj instanceof Dataset) {
784                        final Dataset ds = (Dataset) obj;
785                        if (ShapeUtils.calcSize(iter.getShape()) != ds.getSize()) {
786                                throw new IllegalArgumentException(
787                                                "Number of items in index datasets does not match number of items in dataset");
788                        }
789
790                        final IndexIterator oiter = ds.getIterator();
791
792                        while (iter.hasNext() && oiter.hasNext()) {
793                                setItem((float) ds.getElementDoubleAbs(oiter.index), pos); // GET_ELEMENT_WITH_CAST
794                        }
795                } else {
796                        final float dv = (float) DTypeUtils.toReal(obj); // PRIM_TYPE // FROM_OBJECT
797
798                        while (iter.hasNext()) {
799                                setItem(dv, pos);
800                        }
801                }
802                return this;
803        }
804
805        @Override
806        FloatDataset setSlicedView(Dataset view, Dataset d) {
807                setDirty();
808                final BroadcastSelfIterator it = BroadcastSelfIterator.createIterator(view, d);
809
810                while (it.hasNext()) {
811                        data[it.aIndex] = (float) it.bDouble; // BCAST_WITH_CAST d.getElementDoubleAbs(it.bIndex);
812                }
813                return this;
814        }
815
816        @Override
817        public FloatDataset setSlice(final Object obj, final IndexIterator siter) {
818                setDirty();
819
820                if (obj instanceof IDataset) {
821                        final IDataset ds = (IDataset) obj;
822                        final int[] oshape = ds.getShape();
823
824                        if (!ShapeUtils.areShapesCompatible(siter.getShape(), oshape)) {
825                                throw new IllegalArgumentException(String.format(
826                                                "Input dataset is not compatible with slice: %s cf %s", Arrays.toString(oshape),
827                                                Arrays.toString(siter.getShape())));
828                        }
829
830                        if (ds instanceof Dataset) {
831                                final Dataset ads = (Dataset) ds;
832                                final IndexIterator oiter = ads.getIterator();
833
834                                while (siter.hasNext() && oiter.hasNext())
835                                        data[siter.index] = (float) ads.getElementDoubleAbs(oiter.index); // GET_ELEMENT_WITH_CAST
836                        } else {
837                                final IndexIterator oiter = new PositionIterator(oshape);
838                                final int[] pos = oiter.getPos();
839
840                                while (siter.hasNext() && oiter.hasNext())
841                                        data[siter.index] = ds.getFloat(pos); // PRIM_TYPE
842                        }
843                } else {
844                        try {
845                                float v = (float) DTypeUtils.toReal(obj); // PRIM_TYPE // FROM_OBJECT
846
847                                while (siter.hasNext())
848                                        data[siter.index] = v;
849                        } catch (IllegalArgumentException e) {
850                                throw new IllegalArgumentException("Object for setting slice is not a dataset or number");
851                        }
852                }
853                return this;
854        }
855
856        @Override
857        public void copyItemsFromAxes(final int[] pos, final boolean[] axes, final Dataset dest) {
858                float[] ddata = (float[]) dest.getBuffer(); // PRIM_TYPE
859
860                SliceIterator siter = getSliceIteratorFromAxes(pos, axes);
861                int[] sshape = ShapeUtils.squeezeShape(siter.getShape(), false);
862
863                IndexIterator diter = dest.getSliceIterator(null, sshape, null);
864
865                if (ddata.length < ShapeUtils.calcSize(sshape)) {
866                        throw new IllegalArgumentException("destination array is not large enough");
867                }
868
869                dest.setDirty();
870                while (siter.hasNext() && diter.hasNext()) {
871                        ddata[diter.index] = data[siter.index];
872                }
873        }
874
875        @Override
876        public void setItemsOnAxes(final int[] pos, final boolean[] axes, final Object src) {
877                setDirty();
878                float[] sdata = (float[]) src; // PRIM_TYPE
879
880                SliceIterator siter = getSliceIteratorFromAxes(pos, axes);
881
882                if (sdata.length < ShapeUtils.calcSize(siter.getShape())) {
883                        throw new IllegalArgumentException("destination array is not large enough");
884                }
885
886                for (int i = 0; siter.hasNext(); i++) {
887                        data[siter.index] = sdata[i];
888                }
889        }
890
891        private List<int[]> findPositions(final float value) { // PRIM_TYPE
892                IndexIterator iter = getIterator(true);
893                List<int[]> posns = new ArrayList<int[]>();
894                int[] pos = iter.getPos();
895
896                if (Float.isNaN(value)) { // CLASS_TYPE // REAL_ONLY
897                        while (iter.hasNext()) { // REAL_ONLY
898                                if (Double.isNaN(data[iter.index])) { // REAL_ONLY
899                                        posns.add(pos.clone()); // REAL_ONLY
900                                } // REAL_ONLY
901                        } // REAL_ONLY
902                } else // REAL_ONLY
903                {
904                        while (iter.hasNext()) {
905                                if (data[iter.index] == value) {
906                                        posns.add(pos.clone());
907                                }
908                        }
909                }
910                return posns;
911        }
912
913        @Override
914        public int[] maxPos(boolean... ignoreInvalids) {
915                StatisticsMetadata<Number> md = getStats(); // PRIM_TYPE
916                // StatisticsMetadata<Number> md = getStats(); // BOOLEAN_USE
917                // StatisticsMetadata<String> md = getStringStats(); // OBJECT_USE
918                List<int[]> max = md.getMaximumPositions(ignoreInvalids);
919
920                if (max == null) {
921                        max = findPositions(md.getMaximum(ignoreInvalids).floatValue()); // PRIM_TYPE
922                        // max = findPositions(md.getMaximum(ignoreInvalids).intValue() != 0); // BOOLEAN_USE
923                        // max = findPositions(md.getMaximum(ignoreInvalids).toString()); // OBJECT_USE
924
925                        md.setMaximumPositions(max);
926                }
927
928                return max.get(0); // first maximum
929        }
930
931        @Override
932        public int[] minPos(boolean... ignoreInvalids) {
933                StatisticsMetadata<Number> md = getStats(); // PRIM_TYPE
934                // StatisticsMetadata<Number> md = getStats(); // BOOLEAN_USE
935                // StatisticsMetadata<String> md = getStringStats(); // OBJECT_USE
936                List<int[]> min = md.getMinimumPositions(ignoreInvalids);
937
938                if (min == null) {
939                        min = findPositions(md.getMinimum(ignoreInvalids).floatValue()); // PRIM_TYPE
940                        // min = findPositions(md.getMinimum(ignoreInvalids).intValue() != 0); // BOOLEAN_USE
941                        // min = findPositions(md.getMinimum(ignoreInvalids).toString()); // OBJECT_USE
942
943                        md.setMinimumPositions(min);
944                }
945
946                return min.get(0); // first minimum
947        }
948
949        @Override
950        public boolean containsNans() {
951                IndexIterator iter = getIterator(); // REAL_ONLY
952                while (iter.hasNext()) { // REAL_ONLY
953                        if (Float.isNaN(data[iter.index])) // CLASS_TYPE // REAL_ONLY
954                                return true; // REAL_ONLY
955                } // REAL_ONLY
956                return false;
957        }
958
959        @Override
960        public boolean containsInfs() {
961                IndexIterator iter = getIterator(); // REAL_ONLY
962                while (iter.hasNext()) { // REAL_ONLY
963                        if (Float.isInfinite(data[iter.index])) // CLASS_TYPE // REAL_ONLY
964                                return true; // REAL_ONLY
965                } // REAL_ONLY
966                return false;
967        }
968
969        @Override
970        public boolean containsInvalidNumbers() {
971                IndexIterator iter = getIterator(); // REAL_ONLY
972                while (iter.hasNext()) { // REAL_ONLY
973                        float x = data[iter.index]; // PRIM_TYPE // REAL_ONLY
974                        if (Float.isNaN(x) || Float.isInfinite(x)) // CLASS_TYPE // REAL_ONLY
975                                return true; // REAL_ONLY
976                } // REAL_ONLY
977                return false;
978        }
979
980        @Override
981        public FloatDataset iadd(final Object b) {
982                setDirty();
983                Dataset bds = b instanceof Dataset ? (Dataset) b : DatasetFactory.createFromObject(b);
984                boolean useLong = bds.getElementClass().equals(Long.class);
985                if (bds.getSize() == 1) {
986                        final IndexIterator it = getIterator();
987                        if (useLong) {
988                                final long lb = bds.getElementLongAbs(0);
989                                while (it.hasNext()) {
990                                        data[it.index] += lb;
991                                }
992                        } else {
993                                final double db = bds.getElementDoubleAbs(0);
994                                while (it.hasNext()) {
995                                        data[it.index] += db;
996                                }
997                        }
998                } else {
999                        final BroadcastSelfIterator it = BroadcastSelfIterator.createIterator(this, bds);
1000                        it.setOutputDouble(!useLong);
1001                        if (useLong) {
1002                                while (it.hasNext()) {
1003                                        data[it.aIndex] += it.bLong;
1004                                }
1005                        } else {
1006                                while (it.hasNext()) {
1007                                        data[it.aIndex] += it.bDouble;
1008                                }
1009                        }
1010                }
1011                return this;
1012        }
1013
1014        @Override
1015        public FloatDataset isubtract(final Object b) {
1016                setDirty();
1017                Dataset bds = b instanceof Dataset ? (Dataset) b : DatasetFactory.createFromObject(b);
1018                boolean useLong = bds.getElementClass().equals(Long.class);
1019                if (bds.getSize() == 1) {
1020                        final IndexIterator it = getIterator();
1021                        if (useLong) {
1022                                final long lb = bds.getElementLongAbs(0);
1023                                while (it.hasNext()) {
1024                                        data[it.index] -= lb;
1025                                }
1026                        } else {
1027                                final double db = bds.getElementDoubleAbs(0);
1028                                while (it.hasNext()) {
1029                                        data[it.index] -= db;
1030                                }
1031                        }
1032                } else {
1033                        final BroadcastSelfIterator it = BroadcastSelfIterator.createIterator(this, bds);
1034                        if (useLong) {
1035                                it.setOutputDouble(false);
1036                                while (it.hasNext()) {
1037                                        data[it.aIndex] -= it.bLong;
1038                                }
1039                        } else {
1040                                it.setOutputDouble(true);
1041                                while (it.hasNext()) {
1042                                        data[it.aIndex] -= it.bDouble;
1043                                }
1044                        }
1045                }
1046                return this;
1047        }
1048
1049        @Override
1050        public FloatDataset imultiply(final Object b) {
1051                setDirty();
1052                Dataset bds = b instanceof Dataset ? (Dataset) b : DatasetFactory.createFromObject(b);
1053                boolean useLong = bds.getElementClass().equals(Long.class);
1054                if (bds.getSize() == 1) {
1055                        final IndexIterator it = getIterator();
1056                        if (useLong) {
1057                                final long lb = bds.getElementLongAbs(0);
1058                                while (it.hasNext()) {
1059                                        data[it.index] *= lb;
1060                                }
1061                        } else {
1062                                final double db = bds.getElementDoubleAbs(0);
1063                                while (it.hasNext()) {
1064                                        data[it.index] *= db;
1065                                }
1066                        }
1067                } else {
1068                        final BroadcastSelfIterator it = BroadcastSelfIterator.createIterator(this, bds);
1069                        it.setOutputDouble(!useLong);
1070                        if (useLong) {
1071                                while (it.hasNext()) {
1072                                        data[it.aIndex] *= it.bLong;
1073                                }
1074                        } else {
1075                                while (it.hasNext()) {
1076                                        data[it.aIndex] *= it.bDouble;
1077                                }
1078                        }
1079                }
1080                return this;
1081        }
1082
1083        @Override
1084        public FloatDataset idivide(final Object b) {
1085                setDirty();
1086                Dataset bds = b instanceof Dataset ? (Dataset) b : DatasetFactory.createFromObject(b);
1087                boolean useLong = bds.getElementClass().equals(Long.class);
1088                if (bds.getSize() == 1) {
1089                        if (useLong) {
1090                                final long lb = bds.getElementLongAbs(0);
1091                                // if (lb == 0) { // INT_USE
1092                                //      fill(0); // INT_USE
1093                                // } else { // INT_USE
1094                                final IndexIterator it = getIterator();
1095                                while (it.hasNext()) {
1096                                        data[it.index] /= lb;
1097                                }
1098                                // } // INT_USE
1099                        } else {
1100                                final double db = bds.getElementDoubleAbs(0);
1101                                // if (db == 0) { // INT_USE
1102                                //      fill(0); // INT_USE
1103                                // } else { // INT_USE
1104                                final IndexIterator it = getIterator();
1105                                while (it.hasNext()) {
1106                                        data[it.index] /= db;
1107                                }
1108                                // } // INT_USE
1109                        }
1110                } else {
1111                        final BroadcastSelfIterator it = BroadcastSelfIterator.createIterator(this, bds);
1112                        it.setOutputDouble(!useLong);
1113                        if (useLong) {
1114                                while (it.hasNext()) {
1115                                        // if (it.bLong == 0) { // INT_USE
1116                                        //      data[it.aIndex] = 0; // INT_USE
1117                                        // } else { // INT_USE
1118                                        data[it.aIndex] /= it.bLong;
1119                                        // } // INT_USE
1120                                }
1121                        } else {
1122                                while (it.hasNext()) {
1123                                        // if (it.bDouble == 0) { // INT_USE
1124                                        //      data[it.aIndex] = 0; // INT_USE
1125                                        // } else { // INT_USE
1126                                        data[it.aIndex] /= it.bDouble;
1127                                        // } // INT_USE
1128                                }
1129                        }
1130                }
1131                return this;
1132        }
1133
1134        @Override
1135        public FloatDataset ifloor() {
1136                setDirty(); // REAL_ONLY
1137                IndexIterator it = getIterator(); // REAL_ONLY
1138                while (it.hasNext()) { // REAL_ONLY
1139                        data[it.index] = (float) Math.floor(data[it.index]); // PRIM_TYPE // REAL_ONLY // ADD_CAST
1140                } // REAL_ONLY
1141                return this;
1142        }
1143
1144        @Override
1145        public FloatDataset iremainder(final Object b) {
1146                setDirty();
1147                Dataset bds = b instanceof Dataset ? (Dataset) b : DatasetFactory.createFromObject(b);
1148                boolean useLong = bds.getElementClass().equals(Long.class);
1149                if (bds.getSize() == 1) {
1150                        if (useLong) {
1151                                final long lb = bds.getElementLongAbs(0);
1152                                // if (lb == 0) { // INT_USE
1153                                //      fill(0); // INT_USE
1154                                // } else { // INT_USE
1155                                final IndexIterator it = getIterator();
1156                                while (it.hasNext()) {
1157                                        data[it.index] %= lb;
1158                                }
1159                                // } // INT_USE
1160                        } else {
1161                                final long lb = bds.getElementLongAbs(0);
1162                                // if (lb == 0) { // INT_USE
1163                                //      fill(0); // INT_USE
1164                                // } else { // INT_USE
1165                                final IndexIterator it = getIterator();
1166                                while (it.hasNext()) {
1167                                        data[it.index] %= lb;
1168                                }
1169                                // } // INT_USE
1170                        }
1171                } else {
1172                        final BroadcastSelfIterator it = BroadcastSelfIterator.createIterator(this, bds);
1173                        it.setOutputDouble(!useLong);
1174                        if (useLong) {
1175                                while (it.hasNext()) {
1176                                        data[it.aIndex] %= it.bLong; // INT_EXCEPTION
1177                                }
1178                        } else {
1179                                while (it.hasNext()) {
1180                                        data[it.aIndex] %= it.bDouble; // INT_EXCEPTION
1181                                }
1182                        }
1183                }
1184                return this;
1185        }
1186
1187        @Override
1188        public FloatDataset ipower(final Object b) {
1189                setDirty();
1190                Dataset bds = b instanceof Dataset ? (Dataset) b : DatasetFactory.createFromObject(b);
1191                if (bds.getSize() == 1) {
1192                        final double vr = bds.getElementDoubleAbs(0);
1193                        final IndexIterator it = getIterator();
1194                        if (bds.isComplex()) {
1195                                final double vi = bds.getElementDoubleAbs(1);
1196                                if (vi == 0) {
1197                                        while (it.hasNext()) {
1198                                                final double v = Math.pow(data[it.index], vr);
1199                                                // if (Double.isInfinite(v) || Double.isNaN(v)) { // INT_USE
1200                                                //      data[it.index] = 0; // INT_USE
1201                                                // } else { // INT_USE
1202                                                data[it.index] = (float) v; // PRIM_TYPE_LONG // ADD_CAST
1203                                                // } // INT_USE
1204                                        }
1205                                } else {
1206                                        final Complex zv = new Complex(vr, vi);
1207                                        while (it.hasNext()) {
1208                                                Complex zd = new Complex(data[it.index], 0);
1209                                                final double v = zd.pow(zv).getReal();
1210                                                // if (Double.isInfinite(v) || Double.isNaN(v)) { // INT_USE
1211                                                //      data[it.index] = 0; // INT_USE
1212                                                // } else { // INT_USE
1213                                                data[it.index] = (float) v; // PRIM_TYPE_LONG // ADD_CAST
1214                                                // } // INT_USE
1215                                        }
1216                                }
1217                        } else {// NAN_OMIT
1218                                while (it.hasNext()) {
1219                                        final double v = Math.pow(data[it.index], vr);
1220                                        // if (Double.isInfinite(v) || Double.isNaN(v)) { // INT_USE
1221                                        //      data[it.index] = 0; // INT_USE
1222                                        // } else { // INT_USE
1223                                        data[it.index] = (float) v; // PRIM_TYPE_LONG // ADD_CAST
1224                                        // } // INT_USE
1225                                }
1226                        }
1227                } else {
1228                        final BroadcastIterator it = BroadcastIterator.createIterator(this, bds);
1229                        it.setOutputDouble(true);
1230                        if (bds.isComplex()) {
1231                                while (it.hasNext()) {
1232                                        final Complex zv = new Complex(it.bDouble, bds.getElementDoubleAbs(it.bIndex + 1));
1233                                        final double v = new Complex(it.aDouble, 0).pow(zv).getReal();
1234                                        // if (Double.isInfinite(v) || Double.isNaN(v)) { // INT_USE
1235                                        //      data[it.aIndex] = 0; // INT_USE
1236                                        // } else { // INT_USE
1237                                        data[it.aIndex] = (float) v; // PRIM_TYPE_LONG // ADD_CAST
1238                                        // } // INT_USE
1239                                }
1240                        } else {// NAN_OMIT
1241                                while (it.hasNext()) {
1242                                        final double v = Math.pow(it.aDouble, it.bDouble);
1243                                        // if (Double.isInfinite(v) || Double.isNaN(v)) { // INT_USE
1244                                        //      data[it.aIndex] = 0; // INT_USE
1245                                        // } else { // INT_USE
1246                                        data[it.aIndex] = (float) v; // PRIM_TYPE_LONG // ADD_CAST
1247                                        // } // INT_USE
1248                                }
1249                        }
1250                }
1251                return this;
1252        }
1253
1254        @Override
1255        public double residual(final Object b, final Dataset w, boolean ignoreNaNs) {
1256                Dataset bds = b instanceof Dataset ? (Dataset) b : DatasetFactory.createFromObject(b);
1257                final BroadcastIterator it = BroadcastIterator.createIterator(this, bds);
1258                it.setOutputDouble(true);
1259                double sum = 0;
1260                double comp = 0;
1261                if (ignoreNaNs) { // REAL_ONLY
1262                        if (w == null) { // REAL_ONLY
1263                                while (it.hasNext()) { // REAL_ONLY
1264                                        final double diff = it.aDouble - it.bDouble; // REAL_ONLY
1265                                        if (Double.isNaN(diff)) // REAL_ONLY
1266                                                continue; // REAL_ONLY
1267                                        final double err = diff * diff - comp; // REAL_ONLY
1268                                        final double temp = sum + err; // REAL_ONLY
1269                                        comp = (temp - sum) - err; // REAL_ONLY
1270                                        sum = temp; // REAL_ONLY
1271                                } // REAL_ONLY
1272                        } else { // REAL_ONLY
1273                                IndexIterator itw = w.getIterator(); // REAL_ONLY
1274                                while (it.hasNext() && itw.hasNext()) { // REAL_ONLY
1275                                        final double diff = it.aDouble - it.bDouble; // REAL_ONLY
1276                                        if (Double.isNaN(diff)) // REAL_ONLY
1277                                                continue; // REAL_ONLY
1278                                        final double err = diff * diff * w.getElementDoubleAbs(itw.index) - comp; // REAL_ONLY
1279                                        final double temp = sum + err; // REAL_ONLY
1280                                        comp = (temp - sum) - err; // REAL_ONLY
1281                                        sum = temp; // REAL_ONLY
1282                                } // REAL_ONLY
1283                        } // REAL_ONLY
1284                } else // REAL_ONLY
1285                {
1286                        if (w == null) {
1287                                while (it.hasNext()) {
1288                                        final double diff = it.aDouble - it.bDouble;
1289                                        final double err = diff * diff - comp;
1290                                        final double temp = sum + err;
1291                                        comp = (temp - sum) - err;
1292                                        sum = temp;
1293                                }
1294                        } else {
1295                                IndexIterator itw = w.getIterator();
1296                                while (it.hasNext() && itw.hasNext()) {
1297                                        final double diff = it.aDouble - it.bDouble;
1298                                        final double err = diff * diff * w.getElementDoubleAbs(itw.index) - comp;
1299                                        final double temp = sum + err;
1300                                        comp = (temp - sum) - err;
1301                                        sum = temp;
1302                                }
1303                        }
1304                }
1305                return sum;
1306        }
1307}