sis-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From desruisse...@apache.org
Subject svn commit: r1770970 - in /sis/branches/JDK8/core/sis-feature/src: main/java/org/apache/sis/feature/CharacteristicTypeMap.java main/java/org/apache/sis/feature/DefaultFeatureType.java test/java/org/apache/sis/feature/CharacteristicTypeMapTest.java
Date Wed, 23 Nov 2016 13:56:17 GMT
Author: desruisseaux
Date: Wed Nov 23 13:56:17 2016
New Revision: 1770970

URL: http://svn.apache.org/viewvc?rev=1770970&view=rev
Log:
Attribute.characteristics().get(String) should accept short names (i.e. allow the scope to
be omitted when there is no ambiguity).
This is the same mechanism than the one already used by FeatureType. Opportunistically generalize
the search for shorter names.

Modified:
    sis/branches/JDK8/core/sis-feature/src/main/java/org/apache/sis/feature/CharacteristicTypeMap.java
    sis/branches/JDK8/core/sis-feature/src/main/java/org/apache/sis/feature/DefaultFeatureType.java
    sis/branches/JDK8/core/sis-feature/src/test/java/org/apache/sis/feature/CharacteristicTypeMapTest.java

Modified: sis/branches/JDK8/core/sis-feature/src/main/java/org/apache/sis/feature/CharacteristicTypeMap.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK8/core/sis-feature/src/main/java/org/apache/sis/feature/CharacteristicTypeMap.java?rev=1770970&r1=1770969&r2=1770970&view=diff
==============================================================================
--- sis/branches/JDK8/core/sis-feature/src/main/java/org/apache/sis/feature/CharacteristicTypeMap.java
[UTF-8] (original)
+++ sis/branches/JDK8/core/sis-feature/src/main/java/org/apache/sis/feature/CharacteristicTypeMap.java
[UTF-8] Wed Nov 23 13:56:17 2016
@@ -18,6 +18,8 @@ package org.apache.sis.feature;
 
 import java.util.Map;
 import java.util.HashMap;
+import org.opengis.util.ScopedName;
+import org.opengis.util.GenericName;
 import org.apache.sis.internal.util.AbstractMap;
 import org.apache.sis.internal.util.CollectionsExt;
 import org.apache.sis.util.collection.Containers;
@@ -45,7 +47,7 @@ import org.opengis.feature.AttributeType
  *
  * @author  Martin Desruisseaux (Geomatys)
  * @since   0.5
- * @version 0.5
+ * @version 0.8
  * @module
  */
 final class CharacteristicTypeMap extends AbstractMap<String,AttributeType<?>>
{
@@ -81,9 +83,9 @@ final class CharacteristicTypeMap extend
      * <p>This method does not clone the {@code characterizedBy} array. If that array
      * is a user-provided argument, then cloning that array is caller responsibility.</p>
      *
-     * @param  source The attribute which is characterized by {@code characterizedBy}.
-     * @param  characterizedBy Characteristics of {@code source}. Should not be empty.
-     * @return A map for this given characteristics.
+     * @param  source  the attribute which is characterized by {@code characterizedBy}.
+     * @param  characterizedBy  characteristics of {@code source}. Should not be empty.
+     * @return a map for this given characteristics.
      * @throws IllegalArgumentException if two characteristics have the same name.
      */
     static CharacteristicTypeMap create(final AttributeType<?> source, final AttributeType<?>[]
characterizedBy) {
@@ -104,20 +106,47 @@ final class CharacteristicTypeMap extend
      * <p>This constructor does not clone the {@code characterizedBy} array. If that
array
      * is a user-provided argument, then cloning that array is caller responsibility.</p>
      *
-     * @param  source The attribute which is characterized by {@code characterizedBy}.
-     * @param  characterizedBy Characteristics of {@code source}. Should not be empty.
+     * @param  source  the attribute which is characterized by {@code characterizedBy}.
+     * @param  characterizedBy  characteristics of {@code source}. Should not be empty.
      * @throws IllegalArgumentException if two characteristics have the same name.
      */
     private CharacteristicTypeMap(final AttributeType<?> source, final AttributeType<?>[]
characterizedBy) {
         this.characterizedBy = characterizedBy;
         int index = 0;
         final Map<String,Integer> indices = new HashMap<>(Containers.hashMapCapacity(characterizedBy.length));
+        final Map<String,Integer> aliases = new HashMap<>();
         for (int i=0; i<characterizedBy.length; i++) {
             final AttributeType<?> attribute = characterizedBy[i];
             ensureNonNullElement("characterizedBy", i, attribute);
-            final String name = AbstractIdentifiedType.toString(attribute.getName(), source,
"characterizedBy", i);
-            if (indices.put(name, index++) != null) {
-                throw new IllegalArgumentException(Errors.format(Errors.Keys.DuplicatedIdentifier_1,
name));
+            GenericName name = attribute.getName();
+            String key = AbstractIdentifiedType.toString(name, source, "characterizedBy",
i);
+            final Integer value = index++;
+            if (indices.put(key, value) != null) {
+                throw new IllegalArgumentException(Errors.format(Errors.Keys.DuplicatedIdentifier_1,
key));
+            }
+            /*
+             * If some characteristics use long name of the form "head:tip", creates short
aliases containing
+             * only the "tip" name for convenience, provided that it does not create ambiguity.
If an alias
+             * could map to two or more characteristics, then that alias is not added. Those
ambiguous aliases
+             * are identified by the -1 value in the 'aliases' map.
+             */
+            while (name instanceof ScopedName) {
+                if (name == (name = ((ScopedName) name).tail())) break;   // Safety against
broken implementations.
+                key = name.toString();
+                if (key == null || (key = key.trim()).isEmpty()) break;   // Safety against
broken implementations.
+                if (aliases.put(key, value) != null) {
+                    aliases.put(key, -1);
+                }
+            }
+        }
+        /*
+         * Copy the aliases only after we finished to create the list of all fully-qualified
names.
+         * The copy operation shall exclude all ambiguous names.
+         */
+        for (final Map.Entry<String,Integer> entry : aliases.entrySet()) {
+            final Integer value = entry.getValue();
+            if (value >= 0) {
+                indices.putIfAbsent(entry.getKey(), value);
             }
         }
         this.indices = CollectionsExt.compact(indices);

Modified: sis/branches/JDK8/core/sis-feature/src/main/java/org/apache/sis/feature/DefaultFeatureType.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK8/core/sis-feature/src/main/java/org/apache/sis/feature/DefaultFeatureType.java?rev=1770970&r1=1770969&r2=1770970&view=diff
==============================================================================
--- sis/branches/JDK8/core/sis-feature/src/main/java/org/apache/sis/feature/DefaultFeatureType.java
[UTF-8] (original)
+++ sis/branches/JDK8/core/sis-feature/src/main/java/org/apache/sis/feature/DefaultFeatureType.java
[UTF-8] Wed Nov 23 13:56:17 2016
@@ -26,10 +26,11 @@ import java.util.IdentityHashMap;
 import java.util.Collection;
 import java.util.Collections;
 import java.util.Iterator;
+import java.util.Objects;
 import java.io.IOException;
 import java.io.ObjectInputStream;
 import org.opengis.util.NameFactory;
-import org.opengis.util.LocalName;
+import org.opengis.util.ScopedName;
 import org.opengis.util.GenericName;
 import org.opengis.util.InternationalString;
 import org.opengis.parameter.ParameterDescriptorGroup;
@@ -40,7 +41,6 @@ import org.apache.sis.internal.util.Unmo
 import org.apache.sis.internal.feature.Resources;
 
 // Branch-dependent imports
-import java.util.Objects;
 import org.opengis.feature.IdentifiedType;
 import org.opengis.feature.PropertyType;
 import org.opengis.feature.AttributeType;
@@ -387,19 +387,18 @@ public class DefaultFeatureType extends
         /*
          * If some properties use long name of the form "head:tip", creates short aliases
containing only the "tip"
          * name for convenience, provided that it does not create ambiguity.  If a short
alias could map to two or
-         * more properties, then this alias is not added.
+         * more properties, then that alias is not added.
          *
          * In the 'aliases' map below, null values will be assigned to ambiguous short names.
          */
         final Map<String, PropertyType> aliases = new LinkedHashMap<>();
         for (final PropertyType property : allProperties) {
-            final GenericName name = property.getName();
-            final LocalName tip = name.tip();
-            if (tip != name) {                                          // Slight optimization
for a common case.
-                final String key = tip.toString();
-                if (key != null && !key.isEmpty() && !key.equals(name.toString()))
{
-                    aliases.put(key, aliases.containsKey(key) ? null : property);
-                }
+            GenericName name = property.getName();
+            while (name instanceof ScopedName) {
+                if (name == (name = ((ScopedName) name).tail())) break;   // Safety against
broken implementations.
+                String key = name.toString();
+                if (key == null || (key = key.trim()).isEmpty()) break;   // Safety against
broken implementations.
+                aliases.put(key, aliases.containsKey(key) ? null : property);
             }
         }
         for (final Map.Entry<String,PropertyType> entry : aliases.entrySet()) {
@@ -411,7 +410,7 @@ public class DefaultFeatureType extends
                     // The 'indices' value may be null if the property is an operation.
                     final Integer value = indices.get(property.getName().toString());
                     if (value != null && indices.put(tip, value) != null) {
-                        throw new AssertionError(tip);  // Should never happen.
+                        throw new AssertionError(tip);                                  //
Should never happen.
                     }
                 }
             }

Modified: sis/branches/JDK8/core/sis-feature/src/test/java/org/apache/sis/feature/CharacteristicTypeMapTest.java
URL: http://svn.apache.org/viewvc/sis/branches/JDK8/core/sis-feature/src/test/java/org/apache/sis/feature/CharacteristicTypeMapTest.java?rev=1770970&r1=1770969&r2=1770970&view=diff
==============================================================================
--- sis/branches/JDK8/core/sis-feature/src/test/java/org/apache/sis/feature/CharacteristicTypeMapTest.java
[UTF-8] (original)
+++ sis/branches/JDK8/core/sis-feature/src/test/java/org/apache/sis/feature/CharacteristicTypeMapTest.java
[UTF-8] Wed Nov 23 13:56:17 2016
@@ -28,6 +28,7 @@ import static org.apache.sis.test.Assert
 
 // Branch-dependent imports
 import org.opengis.feature.AttributeType;
+import org.apache.sis.util.iso.Names;
 
 
 /**
@@ -35,7 +36,7 @@ import org.opengis.feature.AttributeType
  *
  * @author  Martin Desruisseaux (Geomatys)
  * @since   0.5
- * @version 0.5
+ * @version 0.8
  * @module
  */
 @DependsOn(DefaultAttributeTypeTest.class)
@@ -109,4 +110,24 @@ public final strictfp class Characterist
         assertNotSame(temperature, unserialized);
         assertSame(temperature.characteristics(), unserialized.characteristics());
     }
+
+    /**
+     * Tests usage of names in namespaces.
+     */
+    @Test
+    public void testQualifiedNames() {
+        final DefaultAttributeType<?> a1, a2, a3, tp;
+        a1 = new DefaultAttributeType<>(singletonMap(NAME_KEY, Names.parseGenericName(null,
null, "ns1:accuracy")), Float.class, 1, 1, 0.1f);
+        a2 = new DefaultAttributeType<>(singletonMap(NAME_KEY, Names.parseGenericName(null,
null, "ns2:accuracy")), Float.class, 1, 1, 0.1f);
+        a3 = new DefaultAttributeType<>(singletonMap(NAME_KEY, Names.parseGenericName(null,
null, "ns2:s3:units")), String.class, 1, 1, "°C");
+        tp = new DefaultAttributeType<>(singletonMap(NAME_KEY, "temperature"), Float.class,
1, 1, null, a1, a2, a3);
+
+        final Map<String, AttributeType<?>> characteristics = tp.characteristics();
+        assertSame("ns1:accuracy", a1, characteristics.get("ns1:accuracy"));
+        assertSame("ns2:accuracy", a2, characteristics.get("ns2:accuracy"));
+        assertSame("ns2:s3:units", a3, characteristics.get("ns2:s3:units"));
+        assertSame(    "s3:units", a3, characteristics.get(    "s3:units"));
+        assertSame(       "units", a3, characteristics.get(       "units"));
+        assertNull("    accuracy",     characteristics.get("    accuracy"));        // Because
ambiguous.
+    }
 }



Mime
View raw message