]> gerrit.simantics Code Review - simantics/platform.git/blobdiff - bundles/org.simantics.databoard/src/org/simantics/databoard/binding/reflection/BindingRequest.java
Improved Bindings.getBinding(Class) caching for Datatype.class
[simantics/platform.git] / bundles / org.simantics.databoard / src / org / simantics / databoard / binding / reflection / BindingRequest.java
index 4ada936032036b149dd182ac6bb005e138234ffd..51feb39c3815861e4edde721cb4970ddf33898c0 100644 (file)
@@ -1,3 +1,15 @@
+/*******************************************************************************
+ * Copyright (c) 2007, 2018 Association for Decentralized Information Management in
+ * Industry THTH ry.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ *     VTT Technical Research Centre of Finland - initial API and implementation
+ *     Semantum Oy - gitlab #82
+ *******************************************************************************/
 package org.simantics.databoard.binding.reflection;
 
 import java.lang.annotation.Annotation;
@@ -6,13 +18,25 @@ import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Collections;
 import java.util.List;
+import java.util.Map;
+import java.util.WeakHashMap;
+
 import org.simantics.databoard.annotations.ArgumentImpl;
 import org.simantics.databoard.annotations.Arguments;
 import org.simantics.databoard.binding.Binding;
 import org.simantics.databoard.primitives.MutableInteger;
 
 public class BindingRequest {
-       
+
+    /**
+     * A weak cache for signature strings by Class.
+     * Prevents the system from constructing new strings
+     * from Classes for every non-trivial BindingRequest. 
+     */
+    private static final Map<Class<?>, String> signatureCache = Collections.<Class<?>, String>synchronizedMap(new WeakHashMap<>());
+
+    public static final Annotation[] NO_ANNOTATIONS = {};
+
        public static BindingRequest create( Field field )
        {
        Annotation[] annotations = ClassBindingFactory.getFieldAnnotations(field);
@@ -27,8 +51,6 @@ public class BindingRequest {
     /** Annotations */
     public final Annotation[] annotations;
     
-    public final Annotation[] NO_ANNOTATIONS = new Annotation[0];
-    
     public final String className; // eg. java.util.Map
     public final String signature; // eg. Ljava/util/Map;
     public final String descriptor; //eg. Ljava/util/Map<I;I>;
@@ -59,7 +81,18 @@ public class BindingRequest {
             hash = 7*hash + a.hashCode();
         }
     }
-    
+
+    /**
+     * Create BindingRequest
+     * 
+     * @param clazz
+     * @param annotations
+     */
+    public BindingRequest(Class<?> clazz)
+    {
+        this(clazz, NO_ANNOTATIONS);
+    }
+
     /**
      * Create BindingRequest
      * 
@@ -221,8 +254,17 @@ public class BindingRequest {
                if (clazz==float.class) return "F";
                if (clazz==long.class) return "J";
                if (clazz==double.class) return "D";
-               if (clazz.isArray()) return clazz.getName().replaceAll("\\.", "/");             
-               return "L"+clazz.getName().replaceAll("\\.", "/")+";";
+               String cached = signatureCache.get(clazz);
+               if (cached == null) {
+                       cached = clazz.isArray()
+                                       ? clazz.getName().replace('.', '/')
+                                       : "L"+clazz.getName().replace('.', '/')+";";
+                       signatureCache.put(clazz, cached);
+                       //System.out.println("BindingRequest.getSignature: cache miss for " + clazz + " = " + cached);
+               } else {
+                       //System.out.println("BindingRequest.getSignature: cache hit for " + clazz + " = " + cached);
+               }
+               return cached;
     }
     
     @SuppressWarnings("unchecked")