This is an automated email from the ASF dual-hosted git repository. desruisseaux pushed a commit to branch geoapi-4.0 in repository https://gitbox.apache.org/repos/asf/sis.git
commit 4a14235743c18888e32a28e1f0d251be1fd48103 Author: Martin Desruisseaux <[email protected]> AuthorDate: Thu Mar 14 16:40:54 2019 +0100 SampleDimension.getNodataValues() should returns the "no data values" as NaN values. --- .../java/org/apache/sis/coverage/SampleDimension.java | 17 +++++++++++++---- .../org/apache/sis/coverage/SampleDimensionTest.java | 15 ++++++++++++--- 2 files changed, 25 insertions(+), 7 deletions(-) diff --git a/core/sis-raster/src/main/java/org/apache/sis/coverage/SampleDimension.java b/core/sis-raster/src/main/java/org/apache/sis/coverage/SampleDimension.java index 8cb25e4..8d3e220 100644 --- a/core/sis-raster/src/main/java/org/apache/sis/coverage/SampleDimension.java +++ b/core/sis-raster/src/main/java/org/apache/sis/coverage/SampleDimension.java @@ -105,7 +105,7 @@ public class SampleDimension implements Serializable { /** * The transform from samples to real values. May be {@code null} if this sample dimension - * does not define any transform (which is not the same that defining an identity transform). + * does not define any transform (which is not the same than defining an identity transform). * * @see #getTransferFunction() */ @@ -227,7 +227,7 @@ public class SampleDimension implements Serializable { * Returns the background value. If this sample dimensions has quantitative categories, then the background * value should be one of the value returned by {@link #getNoDataValues()}. However this is not mandatory. * - * @return the background value. + * @return the background value, typically (but not necessarily) one of {@link #getNoDataValues()}. */ public Optional<Number> getBackground() { return Optional.ofNullable(background); @@ -244,12 +244,13 @@ public class SampleDimension implements Serializable { */ public Set<Number> getNoDataValues() { if (converse != null) { // Null if SampleDimension does not contain at least one quantitative category. + final boolean isConverted = transferFunction.isIdentity(); final NumberRange<?>[] ranges = new NumberRange<?>[categories.size()]; Class<? extends Number> widestClass = Byte.class; int count = 0; for (final Category category : categories) { final Category converted = category.converted(); - if (category != converted && converted.isConvertedQualitative()) { + if ((isConverted || category != converted) && converted.isConvertedQualitative()) { final NumberRange<?> range = category.range; if (!range.isBounded()) { throw new IllegalStateException(Resources.format(Resources.Keys.CanNotEnumerateValuesInRange_1, range)); @@ -259,7 +260,7 @@ public class SampleDimension implements Serializable { } } if (count != 0) { - final Set<Number> noDataValues = new TreeSet<>(); + final Set<Number> noDataValues = new TreeSet<>(SampleDimension::compare); for (int i=0; i<count; i++) { final NumberRange<?> range = ranges[i]; final Number minimum = range.getMinValue(); @@ -283,6 +284,14 @@ public class SampleDimension implements Serializable { } /** + * Compares as {@code double} values. This method is similar to {@link Double#compare(double,double)} + * except that it also orders NaN values from raw bit patterns. Reminder: NaN values are sorted last. + */ + private static int compare(final Number n1, final Number n2) { + return Category.compare(n1.doubleValue(), n2.doubleValue()); + } + + /** * Returns the range of values occurring in this sample dimension. The range delimits sample values that * can be converted into real values using the {@linkplain #getTransferFunction() transfer function}. * If that function is {@linkplain MathTransform1D#isIdentity() identity}, then the values are already diff --git a/core/sis-raster/src/test/java/org/apache/sis/coverage/SampleDimensionTest.java b/core/sis-raster/src/test/java/org/apache/sis/coverage/SampleDimensionTest.java index e8cbe07..a2d9f50 100644 --- a/core/sis-raster/src/test/java/org/apache/sis/coverage/SampleDimensionTest.java +++ b/core/sis-raster/src/test/java/org/apache/sis/coverage/SampleDimensionTest.java @@ -18,9 +18,11 @@ package org.apache.sis.coverage; import java.util.Set; import java.util.List; +import java.util.Iterator; import org.opengis.referencing.operation.MathTransform1D; import org.apache.sis.referencing.operation.transform.LinearTransform; import org.apache.sis.referencing.operation.transform.TransferFunction; +import org.apache.sis.math.MathFunctions; import org.apache.sis.measure.NumberRange; import org.apache.sis.measure.Units; import org.apache.sis.test.TestCase; @@ -79,7 +81,6 @@ public final strictfp class SampleDimensionTest extends TestCase { final Set<Number> nodataValues = dimension.getNoDataValues(); assertArrayEquals("nodataValues", new Integer[] {0, 1, 255}, nodataValues.toArray()); - assertEquals("nodataValues.size", 0, dimension.forConvertedValues(true).getNoDataValues().size()); NumberRange<?> range = dimension.getSampleRange().get(); assertEquals("minimum", 0, range.getMinDouble(), STRICT); @@ -95,14 +96,22 @@ public final strictfp class SampleDimensionTest extends TestCase { assertFalse ("identity", tr.getTransform().isIdentity()); assertEquals("scale", scale, tr.getScale(), STRICT); assertEquals("offset", offset, tr.getOffset(), STRICT); - + /* + * Verifies SampleDimension properties after we converted integers to real values. + */ final SampleDimension converted = dimension.forConvertedValues(true); assertNotSame(dimension, converted); assertSame (dimension, dimension.forConvertedValues(false)); assertSame (dimension, converted.forConvertedValues(false)); assertSame (converted, converted.forConvertedValues(true)); + assertSame (range, converted.getSampleRange().get()); assertTrue ("identity", converted.getTransferFunction().get().isIdentity()); assertTrue ("background", Double.isNaN(converted.getBackground().get().doubleValue())); + final Iterator<Number> it = converted.getNoDataValues().iterator(); + assertEquals("nodataValues", 0, MathFunctions.toNanOrdinal(it.next().floatValue())); + assertEquals("nodataValues", 1, MathFunctions.toNanOrdinal(it.next().floatValue())); + assertEquals("nodataValues", 255, MathFunctions.toNanOrdinal(it.next().floatValue())); + assertFalse ("nodataValues", it.hasNext()); } /** @@ -117,7 +126,7 @@ public final strictfp class SampleDimensionTest extends TestCase { assertEquals("name", "Temperature", String.valueOf(dimension.getName())); assertEquals("background", Float.NaN, dimension.getBackground().get()); - assertEquals(0, dimension.getNoDataValues().toArray().length); + assertArrayEquals(new Number[] {Float.NaN}, dimension.getNoDataValues().toArray()); NumberRange<?> range = dimension.getSampleRange().get(); assertEquals("minimum", -2f, range.getMinValue());
