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


The following commit(s) were added to refs/heads/geoapi-4.0 by this push:
     new d290d00  AxisDirections.indexOfColinear(…) should be more robust to 
case where more than one axis may be colinear. Multiple axes having the same 
direction may happen with TemporalCRS (e.g. one axis is "runtime" and another 
axis is "time").
d290d00 is described below

commit d290d00399860f62748b43f0a0ab9f01a08919c2
Author: Martin Desruisseaux <[email protected]>
AuthorDate: Tue Mar 19 15:39:30 2019 +0100

    AxisDirections.indexOfColinear(…) should be more robust to case where more 
than one axis may be colinear.
    Multiple axes having the same direction may happen with TemporalCRS (e.g. 
one axis is "runtime" and another axis is "time").
---
 .../sis/internal/metadata/AxisDirections.java      | 56 +++++++++++++++++-----
 .../internal/referencing/ServicesForMetadata.java  |  6 +--
 .../main/java/org/apache/sis/referencing/CRS.java  |  4 +-
 3 files changed, 47 insertions(+), 19 deletions(-)

diff --git 
a/core/sis-metadata/src/main/java/org/apache/sis/internal/metadata/AxisDirections.java
 
b/core/sis-metadata/src/main/java/org/apache/sis/internal/metadata/AxisDirections.java
index 7549a7f..77d92b6 100644
--- 
a/core/sis-metadata/src/main/java/org/apache/sis/internal/metadata/AxisDirections.java
+++ 
b/core/sis-metadata/src/main/java/org/apache/sis/internal/metadata/AxisDirections.java
@@ -25,7 +25,9 @@ import org.opengis.annotation.UML;
 import org.opengis.referencing.cs.AxisDirection;
 import org.opengis.referencing.cs.CoordinateSystem;
 import org.opengis.referencing.cs.CoordinateSystemAxis;
+import org.apache.sis.util.ComparisonMode;
 import org.apache.sis.util.Characters;
+import org.apache.sis.util.Utilities;
 import org.apache.sis.util.Static;
 import org.apache.sis.util.iso.Types;
 import org.apache.sis.measure.Units;
@@ -481,28 +483,56 @@ public final class AxisDirections extends Static {
 
     /**
      * Returns the index of the first dimension in {@code cs} where axes are 
colinear with the {@code subCS} axes.
-     * If no such dimension is found, returns -1.
-     *
-     * @param  cs     the coordinate system which contains all axes.
+     * If no such dimension is found, returns -1. If more than one sequence of 
{@code cs} axes are colinear with
+     * all {@code subCS} axes, then the following rules apply:
+     *
+     * <ol>
+     *   <li>If a sequence of {@code cs} axes are equal to the {@code subCS} 
axes, that sequence has precedence.</li>
+     *   <li>Otherwise if a sequence of {@code cs} axes have similar names 
than the {@code subCS} axes (as determined
+     *       by {@linkplain 
org.apache.sis.referencing.IdentifiedObjects#isHeuristicMatchForName heuristic 
match},
+     *       that sequence has precedence.</li>
+     *   <li>Otherwise the index of the first sequence if returned, regardless 
axis names.</li>
+     * </ol>
+     *
+     * @param  cs     the coordinate system which contains all axes, or {@code 
null}.
      * @param  subCS  the coordinate system to search into {@code cs}.
      * @return the first dimension of a sequence of axes colinear with {@code 
subCS} axes, or {@code -1} if none.
      *
      * @since 0.5
      */
     public static int indexOfColinear(final CoordinateSystem cs, final 
CoordinateSystem subCS) {
-        final int dim = indexOfColinear(cs, subCS.getAxis(0).getDirection());
-        if (dim >= 0) {
-            int i = subCS.getDimension();
-            if (dim + i > cs.getDimension()) {
-                return -1;
-            }
-            while (--i > 0) {               // Intentionally exclude 0.
-                if (!isColinear(subCS.getAxis(i).getDirection(), cs.getAxis(i 
+ dim).getDirection())) {
-                    return -1;
+        int fallback = -1;
+        if (cs != null) {
+            boolean fallbackMatches = false;
+            final int subDim = subCS.getDimension();
+            final int limit = cs.getDimension() - subDim;
+next:       for (int i=0; i <= limit; i++) {
+                boolean equal = true;
+                boolean match = true;
+                for (int j=0; j<subDim; j++) {
+                    final CoordinateSystemAxis expected = subCS.getAxis(j);
+                    final CoordinateSystemAxis actual = cs.getAxis(i + j);
+                    if (!isColinear(expected.getDirection(), 
actual.getDirection())) {
+                        continue next;
+                    }
+                    if (equal) {
+                        equal = Utilities.deepEquals(expected, actual, 
ComparisonMode.BY_CONTRACT);
+                        if (equal) continue;
+                    }
+                    if (match) {
+                        match = 
ReferencingServices.getInstance().isHeuristicMatchForName(actual, 
expected.getName().getCode());
+                    }
+                }
+                if (equal) {
+                    return i;
+                }
+                if (fallback < 0 | (match & !fallbackMatches)) {
+                    fallbackMatches = match;
+                    fallback = i;
                 }
             }
         }
-        return dim;
+        return fallback;
     }
 
     /**
diff --git 
a/core/sis-referencing/src/main/java/org/apache/sis/internal/referencing/ServicesForMetadata.java
 
b/core/sis-referencing/src/main/java/org/apache/sis/internal/referencing/ServicesForMetadata.java
index b0f3b63..2ea2184 100644
--- 
a/core/sis-referencing/src/main/java/org/apache/sis/internal/referencing/ServicesForMetadata.java
+++ 
b/core/sis-referencing/src/main/java/org/apache/sis/internal/referencing/ServicesForMetadata.java
@@ -266,7 +266,7 @@ public final class ServicesForMetadata extends 
ReferencingServices {
             dim = 0;
         } else {
             dim = AxisDirections.indexOfColinear(crs.getCoordinateSystem(), 
verticalCRS.getCoordinateSystem());
-            assert dim >= 0 : crs; // Should not fail since 'verticalCRS' has 
been extracted from 'crs' by the caller.
+            assert dim >= 0 : crs;      // Should not fail since 'verticalCRS' 
has been extracted from 'crs' by the caller.
         }
         target.setMinimumValue(envelope.getMinimum(dim));
         target.setMaximumValue(envelope.getMaximum(dim));
@@ -287,7 +287,7 @@ public final class ServicesForMetadata extends 
ReferencingServices {
             final CoordinateReferenceSystem crs, final TemporalCRS temporalCRS)
     {
         final int dim = 
AxisDirections.indexOfColinear(crs.getCoordinateSystem(), 
temporalCRS.getCoordinateSystem());
-        assert dim >= 0 : crs; // Should not fail since 'temporalCRS' has been 
extracted from 'crs' by the caller.
+        assert dim >= 0 : crs;      // Should not fail since 'temporalCRS' has 
been extracted from 'crs' by the caller.
         final DefaultTemporalCRS converter = 
DefaultTemporalCRS.castOrCopy(temporalCRS);
         
target.setBounds(TemporalUtilities.toDate(converter.toInstant(envelope.getMinimum(dim))),
                          
TemporalUtilities.toDate(converter.toInstant(envelope.getMaximum(dim))));
@@ -354,7 +354,7 @@ public final class ServicesForMetadata extends 
ReferencingServices {
     public void setBounds(final Envelope envelope, final DefaultTemporalExtent 
target) throws TransformException {
         final CoordinateReferenceSystem crs = 
envelope.getCoordinateReferenceSystem();
         final TemporalCRS temporalCRS = CRS.getTemporalComponent(crs);
-        if (temporalCRS == null) { // Mandatory for the conversion from 
numbers to dates.
+        if (temporalCRS == null) {                          // Mandatory for 
the conversion from numbers to dates.
             throw new 
TransformException(dimensionNotFound(Resources.Keys.MissingTemporalDimension_1, 
crs));
         }
         setTemporalExtent(envelope, target, crs, temporalCRS);
diff --git 
a/core/sis-referencing/src/main/java/org/apache/sis/referencing/CRS.java 
b/core/sis-referencing/src/main/java/org/apache/sis/referencing/CRS.java
index f1e837d..054685c 100644
--- a/core/sis-referencing/src/main/java/org/apache/sis/referencing/CRS.java
+++ b/core/sis-referencing/src/main/java/org/apache/sis/referencing/CRS.java
@@ -1196,9 +1196,7 @@ public final class CRS extends Static {
      *
      * @category information
      */
-    public static VerticalCRS getVerticalComponent(final 
CoordinateReferenceSystem crs,
-            final boolean allowCreateEllipsoidal)
-    {
+    public static VerticalCRS getVerticalComponent(final 
CoordinateReferenceSystem crs, final boolean allowCreateEllipsoidal) {
         if (crs instanceof VerticalCRS) {
             return (VerticalCRS) crs;
         }

Reply via email to