Consistent fine-tuning of synchronized and concurrent data structures

In particular, avoiding synchronized Sets and Maps wherever possible (preferring a ConcurrentHashMap even instead of a synchronized Set) and specifying appropriate ConcurrentHashMap initial capacities (even if we end up choosing 16).
This commit is contained in:
Juergen Hoeller
2012-12-12 23:46:26 +01:00
parent a2f8902b3a
commit b9df7d68d9
58 changed files with 380 additions and 387 deletions

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2010 the original author or authors.
* Copyright 2002-2012 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -57,6 +57,7 @@ public abstract class BeanUtils {
private static final Log logger = LogFactory.getLog(BeanUtils.class);
// using WeakHashMap as a Set
private static final Map<Class<?>, Boolean> unknownEditorTypes =
Collections.synchronizedMap(new WeakHashMap<Class<?>, Boolean>());

View File

@@ -22,7 +22,6 @@ import java.beans.Introspector;
import java.beans.PropertyDescriptor;
import java.lang.ref.Reference;
import java.lang.ref.WeakReference;
import java.util.Collections;
import java.util.HashSet;
import java.util.Iterator;
import java.util.LinkedHashMap;
@@ -70,14 +69,14 @@ public class CachedIntrospectionResults {
* Set of ClassLoaders that this CachedIntrospectionResults class will always
* accept classes from, even if the classes do not qualify as cache-safe.
*/
static final Set<ClassLoader> acceptedClassLoaders = Collections.synchronizedSet(new HashSet<ClassLoader>());
static final Set<ClassLoader> acceptedClassLoaders = new HashSet<ClassLoader>();
/**
* Map keyed by class containing CachedIntrospectionResults.
* Needs to be a WeakHashMap with WeakReferences as values to allow
* for proper garbage collection in case of multiple class loaders.
*/
static final Map<Class, Object> classCache = Collections.synchronizedMap(new WeakHashMap<Class, Object>());
static final Map<Class, Object> classCache = new WeakHashMap<Class, Object>();
/**
@@ -94,7 +93,9 @@ public class CachedIntrospectionResults {
*/
public static void acceptClassLoader(ClassLoader classLoader) {
if (classLoader != null) {
acceptedClassLoaders.add(classLoader);
synchronized (acceptedClassLoaders) {
acceptedClassLoaders.add(classLoader);
}
}
}
@@ -137,7 +138,10 @@ public class CachedIntrospectionResults {
*/
static CachedIntrospectionResults forClass(Class beanClass) throws BeansException {
CachedIntrospectionResults results;
Object value = classCache.get(beanClass);
Object value;
synchronized (classCache) {
value = classCache.get(beanClass);
}
if (value instanceof Reference) {
Reference ref = (Reference) value;
results = (CachedIntrospectionResults) ref.get();
@@ -149,14 +153,18 @@ public class CachedIntrospectionResults {
if (ClassUtils.isCacheSafe(beanClass, CachedIntrospectionResults.class.getClassLoader()) ||
isClassLoaderAccepted(beanClass.getClassLoader())) {
results = new CachedIntrospectionResults(beanClass);
classCache.put(beanClass, results);
synchronized (classCache) {
classCache.put(beanClass, results);
}
}
else {
if (logger.isDebugEnabled()) {
logger.debug("Not strongly caching class [" + beanClass.getName() + "] because it is not cache-safe");
}
results = new CachedIntrospectionResults(beanClass);
classCache.put(beanClass, new WeakReference<CachedIntrospectionResults>(results));
synchronized (classCache) {
classCache.put(beanClass, new WeakReference<CachedIntrospectionResults>(results));
}
}
}
return results;
@@ -172,8 +180,10 @@ public class CachedIntrospectionResults {
private static boolean isClassLoaderAccepted(ClassLoader classLoader) {
// Iterate over array copy in order to avoid synchronization for the entire
// ClassLoader check (avoiding a synchronized acceptedClassLoaders Iterator).
ClassLoader[] acceptedLoaderArray =
acceptedClassLoaders.toArray(new ClassLoader[acceptedClassLoaders.size()]);
ClassLoader[] acceptedLoaderArray;
synchronized (acceptedClassLoaders) {
acceptedLoaderArray = acceptedClassLoaders.toArray(new ClassLoader[acceptedClassLoaders.size()]);
}
for (ClassLoader registeredLoader : acceptedLoaderArray) {
if (isUnderneathClassLoader(classLoader, registeredLoader)) {
return true;

View File

@@ -119,10 +119,10 @@ public class AutowiredAnnotationBeanPostProcessor extends InstantiationAwareBean
private ConfigurableListableBeanFactory beanFactory;
private final Map<Class<?>, Constructor<?>[]> candidateConstructorsCache =
new ConcurrentHashMap<Class<?>, Constructor<?>[]>();
new ConcurrentHashMap<Class<?>, Constructor<?>[]>(64);
private final Map<Class<?>, InjectionMetadata> injectionMetadataCache =
new ConcurrentHashMap<Class<?>, InjectionMetadata>();
new ConcurrentHashMap<Class<?>, InjectionMetadata>(64);
/**

View File

@@ -24,8 +24,6 @@ import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import java.util.Collection;
import java.util.Collections;
import java.util.Iterator;
import java.util.LinkedHashSet;
import java.util.LinkedList;
import java.util.Map;
@@ -85,7 +83,7 @@ public class InitDestroyAnnotationBeanPostProcessor
private int order = Ordered.LOWEST_PRECEDENCE;
private transient final Map<Class<?>, LifecycleMetadata> lifecycleMetadataCache =
new ConcurrentHashMap<Class<?>, LifecycleMetadata>();
new ConcurrentHashMap<Class<?>, LifecycleMetadata>(64);
/**
@@ -240,69 +238,57 @@ public class InitDestroyAnnotationBeanPostProcessor
*/
private class LifecycleMetadata {
private final Set<LifecycleElement> initMethods;
private final Class targetClass;
private final Set<LifecycleElement> destroyMethods;
private final Collection<LifecycleElement> initMethods;
private final Collection<LifecycleElement> destroyMethods;
private volatile Set<LifecycleElement> checkedInitMethods;
private volatile Set<LifecycleElement> checkedDestroyMethods;
public LifecycleMetadata(Class<?> targetClass, Collection<LifecycleElement> initMethods,
Collection<LifecycleElement> destroyMethods) {
if (!initMethods.isEmpty()) {
this.initMethods = Collections.synchronizedSet(new LinkedHashSet<LifecycleElement>(initMethods.size()));
for (LifecycleElement element : initMethods) {
if (logger.isDebugEnabled()) {
logger.debug("Found init method on class [" + targetClass.getName() + "]: " + element);
}
this.initMethods.add(element);
}
}
else {
this.initMethods = Collections.emptySet();
}
if (!destroyMethods.isEmpty()) {
this.destroyMethods = Collections.synchronizedSet(new LinkedHashSet<LifecycleElement>(destroyMethods.size()));
for (LifecycleElement element : destroyMethods) {
if (logger.isDebugEnabled()) {
logger.debug("Found destroy method on class [" + targetClass.getName() + "]: " + element);
}
this.destroyMethods.add(element);
}
}
else {
this.destroyMethods = Collections.emptySet();
}
this.targetClass = targetClass;
this.initMethods = initMethods;
this.destroyMethods = destroyMethods;
}
public void checkConfigMembers(RootBeanDefinition beanDefinition) {
synchronized(this.initMethods) {
for (Iterator<LifecycleElement> it = this.initMethods.iterator(); it.hasNext();) {
String methodIdentifier = it.next().getIdentifier();
if (!beanDefinition.isExternallyManagedInitMethod(methodIdentifier)) {
beanDefinition.registerExternallyManagedInitMethod(methodIdentifier);
}
else {
it.remove();
Set<LifecycleElement> checkedInitMethods = new LinkedHashSet<LifecycleElement>(this.initMethods.size());
for (LifecycleElement element : this.initMethods) {
String methodIdentifier = element.getIdentifier();
if (!beanDefinition.isExternallyManagedInitMethod(methodIdentifier)) {
beanDefinition.registerExternallyManagedInitMethod(methodIdentifier);
checkedInitMethods.add(element);
if (logger.isDebugEnabled()) {
logger.debug("Registered init method on class [" + this.targetClass.getName() + "]: " + element);
}
}
}
synchronized(this.destroyMethods) {
for (Iterator<LifecycleElement> it = this.destroyMethods.iterator(); it.hasNext();) {
String methodIdentifier = it.next().getIdentifier();
if (!beanDefinition.isExternallyManagedDestroyMethod(methodIdentifier)) {
beanDefinition.registerExternallyManagedDestroyMethod(methodIdentifier);
}
else {
it.remove();
Set<LifecycleElement> checkedDestroyMethods = new LinkedHashSet<LifecycleElement>(this.destroyMethods.size());
for (LifecycleElement element : this.destroyMethods) {
String methodIdentifier = element.getIdentifier();
if (!beanDefinition.isExternallyManagedDestroyMethod(methodIdentifier)) {
beanDefinition.registerExternallyManagedDestroyMethod(methodIdentifier);
checkedDestroyMethods.add(element);
if (logger.isDebugEnabled()) {
logger.debug("Registered destroy method on class [" + this.targetClass.getName() + "]: " + element);
}
}
}
this.checkedInitMethods = checkedInitMethods;
this.checkedDestroyMethods = checkedDestroyMethods;
}
public void invokeInitMethods(Object target, String beanName) throws Throwable {
if (!this.initMethods.isEmpty()) {
Collection<LifecycleElement> initMethodsToIterate =
(this.checkedInitMethods != null ? this.checkedInitMethods : this.initMethods);
if (!initMethodsToIterate.isEmpty()) {
boolean debug = logger.isDebugEnabled();
for (LifecycleElement element : this.initMethods) {
for (LifecycleElement element : initMethodsToIterate) {
if (debug) {
logger.debug("Invoking init method on bean '" + beanName + "': " + element.getMethod());
}
@@ -312,9 +298,11 @@ public class InitDestroyAnnotationBeanPostProcessor
}
public void invokeDestroyMethods(Object target, String beanName) throws Throwable {
if (!this.destroyMethods.isEmpty()) {
Collection<LifecycleElement> destroyMethodsToIterate =
(this.checkedDestroyMethods != null ? this.checkedDestroyMethods : this.destroyMethods);
if (!destroyMethodsToIterate.isEmpty()) {
boolean debug = logger.isDebugEnabled();
for (LifecycleElement element : this.destroyMethods) {
for (LifecycleElement element : destroyMethodsToIterate) {
if (debug) {
logger.debug("Invoking destroy method on bean '" + beanName + "': " + element.getMethod());
}

View File

@@ -22,8 +22,6 @@ import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Member;
import java.lang.reflect.Method;
import java.util.Collection;
import java.util.Collections;
import java.util.Iterator;
import java.util.LinkedHashSet;
import java.util.Set;
@@ -50,42 +48,39 @@ public class InjectionMetadata {
private final Log logger = LogFactory.getLog(InjectionMetadata.class);
private final Set<InjectedElement> injectedElements;
private final Class targetClass;
private final Collection<InjectedElement> injectedElements;
private volatile Set<InjectedElement> checkedElements;
public InjectionMetadata(Class targetClass, Collection<InjectedElement> elements) {
if (!elements.isEmpty()) {
this.injectedElements = Collections.synchronizedSet(new LinkedHashSet<InjectedElement>(elements.size()));
for (InjectedElement element : elements) {
if (logger.isDebugEnabled()) {
logger.debug("Found injected element on class [" + targetClass.getName() + "]: " + element);
}
this.injectedElements.add(element);
}
}
else {
this.injectedElements = Collections.emptySet();
}
this.targetClass = targetClass;
this.injectedElements = elements;
}
public void checkConfigMembers(RootBeanDefinition beanDefinition) {
synchronized (this.injectedElements) {
for (Iterator<InjectedElement> it = this.injectedElements.iterator(); it.hasNext();) {
Member member = it.next().getMember();
if (!beanDefinition.isExternallyManagedConfigMember(member)) {
beanDefinition.registerExternallyManagedConfigMember(member);
}
else {
it.remove();
Set<InjectedElement> checkedElements = new LinkedHashSet<InjectedElement>(this.injectedElements.size());
for (InjectedElement element : this.injectedElements) {
Member member = element.getMember();
if (!beanDefinition.isExternallyManagedConfigMember(member)) {
beanDefinition.registerExternallyManagedConfigMember(member);
checkedElements.add(element);
if (logger.isDebugEnabled()) {
logger.debug("Registered injected element on class [" + this.targetClass.getName() + "]: " + element);
}
}
}
this.checkedElements = checkedElements;
}
public void inject(Object target, String beanName, PropertyValues pvs) throws Throwable {
if (!this.injectedElements.isEmpty()) {
Collection<InjectedElement> elementsToIterate =
(this.checkedElements != null ? this.checkedElements : this.injectedElements);
if (!elementsToIterate.isEmpty()) {
boolean debug = logger.isDebugEnabled();
for (InjectedElement element : this.injectedElements) {
for (InjectedElement element : elementsToIterate) {
if (debug) {
logger.debug("Processing injected method of bean '" + beanName + "': " + element);
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2011 the original author or authors.
* Copyright 2002-2012 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -20,10 +20,9 @@ import java.beans.PropertyDescriptor;
import java.lang.annotation.Annotation;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import org.springframework.beans.BeansException;
import org.springframework.beans.PropertyValues;
@@ -89,8 +88,11 @@ public class RequiredAnnotationBeanPostProcessor extends InstantiationAwareBeanP
private ConfigurableListableBeanFactory beanFactory;
/** Cache for validated bean names, skipping re-validation for the same bean */
private final Set<String> validatedBeanNames = Collections.synchronizedSet(new HashSet<String>());
/**
* Cache for validated bean names, skipping re-validation for the same bean
* (using a ConcurrentHashMap as a Set)
*/
private final Map<String, Boolean> validatedBeanNames = new ConcurrentHashMap<String, Boolean>(64);
/**
@@ -137,7 +139,7 @@ public class RequiredAnnotationBeanPostProcessor extends InstantiationAwareBeanP
PropertyValues pvs, PropertyDescriptor[] pds, Object bean, String beanName)
throws BeansException {
if (!this.validatedBeanNames.contains(beanName)) {
if (!this.validatedBeanNames.containsKey(beanName)) {
if (!shouldSkip(this.beanFactory, beanName)) {
List<String> invalidProperties = new ArrayList<String>();
for (PropertyDescriptor pd : pds) {
@@ -149,7 +151,7 @@ public class RequiredAnnotationBeanPostProcessor extends InstantiationAwareBeanP
throw new BeanInitializationException(buildExceptionMessage(invalidProperties, beanName));
}
}
this.validatedBeanNames.add(beanName);
this.validatedBeanNames.put(beanName, Boolean.TRUE);
}
return pvs;
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2009 the original author or authors.
* Copyright 2002-2012 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -16,11 +16,10 @@
package org.springframework.beans.factory.config;
import java.util.Collections;
import java.util.Enumeration;
import java.util.HashSet;
import java.util.Map;
import java.util.Properties;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import org.springframework.beans.BeansException;
import org.springframework.beans.PropertyValue;
@@ -71,8 +70,11 @@ public class PropertyOverrideConfigurer extends PropertyResourceConfigurer {
private boolean ignoreInvalidKeys = false;
/** Contains names of beans that have overrides */
private Set<String> beanNames = Collections.synchronizedSet(new HashSet<String>());
/**
* Contains names of beans that have overrides
* (using a ConcurrentHashMap as a Set)
*/
private Map<String, Boolean> beanNames = new ConcurrentHashMap<String, Boolean>(16);
/**
@@ -128,7 +130,7 @@ public class PropertyOverrideConfigurer extends PropertyResourceConfigurer {
}
String beanName = key.substring(0, separatorIndex);
String beanProperty = key.substring(separatorIndex+1);
this.beanNames.add(beanName);
this.beanNames.put(beanName, Boolean.TRUE);
applyPropertyValue(factory, beanName, beanProperty, value);
if (logger.isDebugEnabled()) {
logger.debug("Property '" + key + "' set to value [" + value + "]");
@@ -159,7 +161,7 @@ public class PropertyOverrideConfigurer extends PropertyResourceConfigurer {
* the named bean
*/
public boolean hasPropertyOverridesFor(String beanName) {
return this.beanNames.contains(beanName);
return this.beanNames.containsKey(beanName);
}
}

View File

@@ -145,11 +145,11 @@ public abstract class AbstractAutowireCapableBeanFactory extends AbstractBeanFac
/** Cache of unfinished FactoryBean instances: FactoryBean name --> BeanWrapper */
private final Map<String, BeanWrapper> factoryBeanInstanceCache =
new ConcurrentHashMap<String, BeanWrapper>();
new ConcurrentHashMap<String, BeanWrapper>(16);
/** Cache of filtered PropertyDescriptors: bean Class -> PropertyDescriptor array */
private final Map<Class, PropertyDescriptor[]> filteredPropertyDescriptorsCache =
new ConcurrentHashMap<Class, PropertyDescriptor[]>();
new ConcurrentHashMap<Class, PropertyDescriptor[]>(64);
/**

View File

@@ -24,7 +24,6 @@ import java.security.PrivilegedActionException;
import java.security.PrivilegedExceptionAction;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.LinkedHashSet;
@@ -151,17 +150,20 @@ public abstract class AbstractBeanFactory extends FactoryBeanRegistrySupport imp
private boolean hasDestructionAwareBeanPostProcessors;
/** Map from scope identifier String to corresponding Scope */
private final Map<String, Scope> scopes = new HashMap<String, Scope>();
private final Map<String, Scope> scopes = new HashMap<String, Scope>(8);
/** Security context used when running with a SecurityManager */
private SecurityContextProvider securityContextProvider;
/** Map from bean name to merged RootBeanDefinition */
private final Map<String, RootBeanDefinition> mergedBeanDefinitions =
new ConcurrentHashMap<String, RootBeanDefinition>();
new ConcurrentHashMap<String, RootBeanDefinition>(64);
/** Names of beans that have already been created at least once */
private final Set<String> alreadyCreated = Collections.synchronizedSet(new HashSet<String>());
/**
* Names of beans that have already been created at least once
* (using a ConcurrentHashMap as a Set)
*/
private final Map<String, Boolean> alreadyCreated = new ConcurrentHashMap<String, Boolean>(64);
/** Names of beans that are currently in creation */
private final ThreadLocal<Object> prototypesCurrentlyInCreation =
@@ -1372,7 +1374,7 @@ public abstract class AbstractBeanFactory extends FactoryBeanRegistrySupport imp
* @param beanName the name of the bean
*/
protected void markBeanAsCreated(String beanName) {
this.alreadyCreated.add(beanName);
this.alreadyCreated.put(beanName, Boolean.TRUE);
}
/**
@@ -1383,7 +1385,7 @@ public abstract class AbstractBeanFactory extends FactoryBeanRegistrySupport imp
* at this point already
*/
protected boolean isBeanEligibleForMetadataCaching(String beanName) {
return this.alreadyCreated.contains(beanName);
return this.alreadyCreated.containsKey(beanName);
}
/**
@@ -1393,7 +1395,7 @@ public abstract class AbstractBeanFactory extends FactoryBeanRegistrySupport imp
* @return <code>true</code> if actually removed, <code>false</code> otherwise
*/
protected boolean removeSingletonIfCreatedForTypeCheckOnly(String beanName) {
if (!this.alreadyCreated.contains(beanName)) {
if (!this.alreadyCreated.containsKey(beanName)) {
removeSingleton(beanName);
return true;
}

View File

@@ -112,7 +112,7 @@ public class DefaultListableBeanFactory extends AbstractAutowireCapableBeanFacto
/** Map from serialized id to factory instance */
private static final Map<String, Reference<DefaultListableBeanFactory>> serializableFactories =
new ConcurrentHashMap<String, Reference<DefaultListableBeanFactory>>();
new ConcurrentHashMap<String, Reference<DefaultListableBeanFactory>>(8);
/** Optional id for this factory, for serialization purposes */
private String serializationId;
@@ -127,16 +127,16 @@ public class DefaultListableBeanFactory extends AbstractAutowireCapableBeanFacto
private AutowireCandidateResolver autowireCandidateResolver = new SimpleAutowireCandidateResolver();
/** Map from dependency type to corresponding autowired value */
private final Map<Class<?>, Object> resolvableDependencies = new HashMap<Class<?>, Object>();
private final Map<Class<?>, Object> resolvableDependencies = new HashMap<Class<?>, Object>(16);
/** Map of bean definition objects, keyed by bean name */
private final Map<String, BeanDefinition> beanDefinitionMap = new ConcurrentHashMap<String, BeanDefinition>();
private final Map<String, BeanDefinition> beanDefinitionMap = new ConcurrentHashMap<String, BeanDefinition>(64);
/** Map of singleton bean names keyed by bean class */
private final Map<Class<?>, String[]> singletonBeanNamesByType = new ConcurrentHashMap<Class<?>, String[]>();
private final Map<Class<?>, String[]> singletonBeanNamesByType = new ConcurrentHashMap<Class<?>, String[]>(64);
/** Map of non-singleton bean names keyed by bean class */
private final Map<Class<?>, String[]> nonSingletonBeanNamesByType = new ConcurrentHashMap<Class<?>, String[]>();
private final Map<Class<?>, String[]> nonSingletonBeanNamesByType = new ConcurrentHashMap<Class<?>, String[]>(64);
/** List of bean definition names, in registration order */
private final List<String> beanDefinitionNames = new ArrayList<String>();

View File

@@ -81,22 +81,22 @@ public class DefaultSingletonBeanRegistry extends SimpleAliasRegistry implements
protected final Log logger = LogFactory.getLog(getClass());
/** Cache of singleton objects: bean name --> bean instance */
private final Map<String, Object> singletonObjects = new ConcurrentHashMap<String, Object>();
private final Map<String, Object> singletonObjects = new ConcurrentHashMap<String, Object>(64);
/** Cache of singleton factories: bean name --> ObjectFactory */
private final Map<String, ObjectFactory> singletonFactories = new HashMap<String, ObjectFactory>();
private final Map<String, ObjectFactory> singletonFactories = new HashMap<String, ObjectFactory>(16);
/** Cache of early singleton objects: bean name --> bean instance */
private final Map<String, Object> earlySingletonObjects = new HashMap<String, Object>();
private final Map<String, Object> earlySingletonObjects = new HashMap<String, Object>(16);
/** Set of registered singletons, containing the bean names in registration order */
private final Set<String> registeredSingletons = new LinkedHashSet<String>(16);
private final Set<String> registeredSingletons = new LinkedHashSet<String>(64);
/** Names of beans that are currently in creation (using a ConcurrentHashMap as a Set) */
private final Map<String, Boolean> singletonsCurrentlyInCreation = new ConcurrentHashMap<String, Boolean>();
private final Map<String, Boolean> singletonsCurrentlyInCreation = new ConcurrentHashMap<String, Boolean>(16);
/** Names of beans currently excluded from in creation checks (using a ConcurrentHashMap as a Set) */
private final Map<String, Boolean> inCreationCheckExclusions = new ConcurrentHashMap<String, Boolean>();
private final Map<String, Boolean> inCreationCheckExclusions = new ConcurrentHashMap<String, Boolean>(16);
/** List of suppressed Exceptions, available for associating related causes */
private Set<Exception> suppressedExceptions;
@@ -108,13 +108,13 @@ public class DefaultSingletonBeanRegistry extends SimpleAliasRegistry implements
private final Map<String, Object> disposableBeans = new LinkedHashMap<String, Object>();
/** Map between containing bean names: bean name --> Set of bean names that the bean contains */
private final Map<String, Set<String>> containedBeanMap = new ConcurrentHashMap<String, Set<String>>();
private final Map<String, Set<String>> containedBeanMap = new ConcurrentHashMap<String, Set<String>>(16);
/** Map between dependent bean names: bean name --> Set of dependent bean names */
private final Map<String, Set<String>> dependentBeanMap = new ConcurrentHashMap<String, Set<String>>();
private final Map<String, Set<String>> dependentBeanMap = new ConcurrentHashMap<String, Set<String>>(64);
/** Map between depending bean names: bean name --> Set of bean names for the bean's dependencies */
private final Map<String, Set<String>> dependenciesForBeanMap = new ConcurrentHashMap<String, Set<String>>();
private final Map<String, Set<String>> dependenciesForBeanMap = new ConcurrentHashMap<String, Set<String>>(64);
public void registerSingleton(String beanName, Object singletonObject) throws IllegalStateException {

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2010 the original author or authors.
* Copyright 2002-2012 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -43,7 +43,7 @@ import org.springframework.beans.factory.FactoryBeanNotInitializedException;
public abstract class FactoryBeanRegistrySupport extends DefaultSingletonBeanRegistry {
/** Cache of singleton objects created by FactoryBeans: FactoryBean name --> object */
private final Map<String, Object> factoryBeanObjectCache = new ConcurrentHashMap<String, Object>();
private final Map<String, Object> factoryBeanObjectCache = new ConcurrentHashMap<String, Object>(16);
/**

View File

@@ -18,9 +18,8 @@ package org.springframework.beans.factory.support;
import java.lang.reflect.Member;
import java.lang.reflect.Method;
import java.util.Collections;
import java.util.HashSet;
import java.util.Set;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import org.springframework.beans.MutablePropertyValues;
import org.springframework.beans.factory.config.BeanDefinition;
@@ -48,11 +47,14 @@ import org.springframework.util.Assert;
*/
public class RootBeanDefinition extends AbstractBeanDefinition {
private final Set<Member> externallyManagedConfigMembers = Collections.synchronizedSet(new HashSet<Member>(0));
// using a ConcurrentHashMap as a Set
private final Map<Member, Boolean> externallyManagedConfigMembers = new ConcurrentHashMap<Member, Boolean>(0);
private final Set<String> externallyManagedInitMethods = Collections.synchronizedSet(new HashSet<String>(0));
// using a ConcurrentHashMap as a Set
private final Map<String, Boolean> externallyManagedInitMethods = new ConcurrentHashMap<String, Boolean>(0);
private final Set<String> externallyManagedDestroyMethods = Collections.synchronizedSet(new HashSet<String>(0));
// using a ConcurrentHashMap as a Set
private final Map<String, Boolean> externallyManagedDestroyMethods = new ConcurrentHashMap<String, Boolean>(0);
private BeanDefinitionHolder decoratedDefinition;
@@ -277,27 +279,27 @@ public class RootBeanDefinition extends AbstractBeanDefinition {
public void registerExternallyManagedConfigMember(Member configMember) {
this.externallyManagedConfigMembers.add(configMember);
this.externallyManagedConfigMembers.put(configMember, Boolean.TRUE);
}
public boolean isExternallyManagedConfigMember(Member configMember) {
return this.externallyManagedConfigMembers.contains(configMember);
return this.externallyManagedConfigMembers.containsKey(configMember);
}
public void registerExternallyManagedInitMethod(String initMethod) {
this.externallyManagedInitMethods.add(initMethod);
this.externallyManagedInitMethods.put(initMethod, Boolean.TRUE);
}
public boolean isExternallyManagedInitMethod(String initMethod) {
return this.externallyManagedInitMethods.contains(initMethod);
return this.externallyManagedInitMethods.containsKey(initMethod);
}
public void registerExternallyManagedDestroyMethod(String destroyMethod) {
this.externallyManagedDestroyMethods.add(destroyMethod);
this.externallyManagedDestroyMethods.put(destroyMethod, Boolean.TRUE);
}
public boolean isExternallyManagedDestroyMethod(String destroyMethod) {
return this.externallyManagedDestroyMethods.contains(destroyMethod);
return this.externallyManagedDestroyMethods.containsKey(destroyMethod);
}
public void setDecoratedDefinition(BeanDefinitionHolder decoratedDefinition) {

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2008 the original author or authors.
* Copyright 2002-2012 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -37,7 +37,7 @@ import org.springframework.util.StringUtils;
public class SimpleBeanDefinitionRegistry extends SimpleAliasRegistry implements BeanDefinitionRegistry {
/** Map of bean definition objects, keyed by bean name */
private final Map<String, BeanDefinition> beanDefinitionMap = new ConcurrentHashMap<String, BeanDefinition>();
private final Map<String, BeanDefinition> beanDefinitionMap = new ConcurrentHashMap<String, BeanDefinition>(64);
public void registerBeanDefinition(String beanName, BeanDefinition beanDefinition)

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2009 the original author or authors.
* Copyright 2002-2012 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -155,7 +155,7 @@ public class DefaultNamespaceHandlerResolver implements NamespaceHandlerResolver
if (logger.isDebugEnabled()) {
logger.debug("Loaded NamespaceHandler mappings: " + mappings);
}
Map<String, Object> handlerMappings = new ConcurrentHashMap<String, Object>();
Map<String, Object> handlerMappings = new ConcurrentHashMap<String, Object>(mappings.size());
CollectionUtils.mergePropertiesIntoMap(mappings, handlerMappings);
this.handlerMappings = handlerMappings;
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2009 the original author or authors.
* Copyright 2002-2012 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -145,7 +145,7 @@ public class PluggableSchemaResolver implements EntityResolver {
if (logger.isDebugEnabled()) {
logger.debug("Loaded schema mappings: " + mappings);
}
Map<String, String> schemaMappings = new ConcurrentHashMap<String, String>();
Map<String, String> schemaMappings = new ConcurrentHashMap<String, String>(mappings.size());
CollectionUtils.mergePropertiesIntoMap(mappings, schemaMappings);
this.schemaMappings = schemaMappings;
}