Commons Collections学习笔记(四)

BeanMap这个Map类用于把一个javaBean转换为Map,在其中存储了javaBean的各个属性的setXXX方法和getXXX方法,属性的类型。

public class BeanMap extends AbstractMap implements Cloneable 
{
    
private transient Object bean;//javaBean对象

    
private transient HashMap readMethods = new HashMap();//getXXX方法集
    private transient HashMap writeMethods = new HashMap();//setXXX方法集
    private transient HashMap types = new HashMap();//成员变量类型集

    
public static final Object[] NULL_ARGUMENTS = {};//空参数集,用于通过reflection调用getXXX方法
    public static HashMap defaultTransformers = new HashMap();//把基本类型映射为transformer类型,后者用于将字符串转换为合适的基本型的包装类
  
    
//默认transformer
    static 
    {
        defaultTransformers.put( Boolean.TYPE, 
new Transformer() 
        {
                
public Object transform( Object input ) 
                {
                    
return Boolean.valueOf( input.toString() );
                }
            }
        );
        defaultTransformers.put( Character.TYPE, 
new Transformer() 
        {
                
public Object transform( Object input ) 
                {
                    
return new Character( input.toString().charAt( 0 ) );
                }
            }
        );
        defaultTransformers.put( Byte.TYPE, 
new Transformer() 
        {
                
public Object transform( Object input ) 
                {
                    
return Byte.valueOf( input.toString() );
                }
            }
        );
        defaultTransformers.put( Short.TYPE, 
new Transformer() 
        {
                
public Object transform( Object input ) 
                {
                    
return Short.valueOf( input.toString() );
                }
            }
        );
        defaultTransformers.put( 
            Integer.TYPE, 
            
new Transformer() {
                
public Object transform( Object input ) {
                    
return Integer.valueOf( input.toString() );
                }
            }
        );
        defaultTransformers.put( Long.TYPE, 
new Transformer() 
        {
                
public Object transform( Object input ) {
                    
return Long.valueOf( input.toString() );
                }
            }
        );
        defaultTransformers.put( Float.TYPE, 
new Transformer() 
        {
                
public Object transform( Object input ) {
                    
return Float.valueOf( input.toString() );
                }
            }
        );
        defaultTransformers.put( Double.TYPE, 
new Transformer() 
        {
                
public Object transform( Object input ) {
                    
return Double.valueOf( input.toString() );
                }
            }
        );
    }

    
public BeanMap(Object bean) {
        
this.bean = bean;
        initialise();
    }


    
public Object clone() throws CloneNotSupportedException {
        BeanMap newMap 
= (BeanMap)super.clone();

        
if(bean == null) {//若底层bean不存在,则返回一个复制的空BeanMap,
            return newMap;
        }
        Object newBean 
= null;            
        Class beanClass 
= null;
        
try {
            beanClass 
= bean.getClass();//底层bean的Class
            newBean = beanClass.newInstance();//实例化一个新的bean
        } catch (Exception e) {
            
// unable to instantiate
            throw new CloneNotSupportedException
                (
"Unable to instantiate the underlying bean \"" +
                 beanClass.getName() + "\"" + e);
        }
            
        
try {
            newMap.setBean(newBean);
        } 
catch (Exception exception) {
            
throw new CloneNotSupportedException
                (
"Unable to set bean in the cloned bean map: " + 
                 exception);
        }
            
        
try {
            
//复制所有可读写的属性
            Iterator readableKeys = readMethods.keySet().iterator();
            
while(readableKeys.hasNext()) {
                Object key 
= readableKeys.next();//属性名称
                if(getWriteMethod(key) != null) {
                    newMap.put(key, get(key));
//放入到新BeanMap中
                }
            }
        } 
catch (Exception exception) {
            
throw new CloneNotSupportedException
                (
"Unable to copy bean values to cloned bean map: " +
                 exception);
        }
        
return newMap;
    }

  
    
public void clear() {
        
if(bean == nullreturn;
        Class beanClass 
= null;
        
try {
            beanClass 
= bean.getClass();
            bean 
= beanClass.newInstance();//重新实例化,一切都回到默认状态
        }
        
catch (Exception e) {
            
throw new UnsupportedOperationException( "Could not create new instance of class: " + beanClass );
        }
    }

    
public Object get(Object name) {//获取指定名称属性的值
        if ( bean != null ) {
            Method method 
= getReadMethod( name );
            
if ( method != null ) {
                
try {
                    
return method.invoke( bean, NULL_ARGUMENTS );
                }
                
catch (  IllegalAccessException e ) {
                    logWarn( e );
                }
                
catch ( IllegalArgumentException e ) {
                    logWarn(  e );
                }
                
catch ( InvocationTargetException e ) {
                    logWarn(  e );
                }
                
catch ( NullPointerException e ) {
                    logWarn(  e );
                }
            }
        }
        
return null;
    }

    
public Object put(Object name, Object value) throws IllegalArgumentException, ClassCastException
    {
//设置指定名称的属性的值
        if ( bean != null ) {
            Object oldValue 
= get( name );//原来的值
            Method method = getWriteMethod( name );
            
if ( method == null ) {
                
throw new IllegalArgumentException( "The bean of type: "+ bean.getClass().getName() + " has no property called: " + name );
            }
            
try {
                Object[] arguments 
= createWriteMethodArguments( method, value );//转换参数
                method.invoke( bean, arguments );//设置新值
                Object newValue = get( name );//获取新设置的值 
                firePropertyChange( name, oldValue, newValue );//fire属性值改变事件
            }
            
catch ( InvocationTargetException e ) {
                logInfo( e );
                
throw new IllegalArgumentException( e.getMessage() );
            }
            
catch ( IllegalAccessException e ) {
                logInfo( e );
                
throw new IllegalArgumentException( e.getMessage() );
            }
            
return oldValue;
        }
        
return null;
    }

    
public Method getReadMethod(String name) {//获取指定名称属性的getXXX方法
        return (Method) readMethods.get(name);
    }

    
public Method getWriteMethod(String name) {//获取指定名称属性的setXXX方法
        return (Method) writeMethods.get(name);
    }

    
private void initialise() 
    {
        
if(getBean() == nullreturn;
        Class  beanClass 
= getBean().getClass();//bean的Class
        try 
        {
            
//BeanInfo beanInfo = Introspector.getBeanInfo( bean, null );
            BeanInfo beanInfo = Introspector.getBeanInfo( beanClass );//bean的信息
            PropertyDescriptor[] propertyDescriptors = beanInfo.getPropertyDescriptors();
            
if ( propertyDescriptors != null ) 
            {
                
for ( int i = 0; i < propertyDescriptors.length; i++ ) 
                {
                    PropertyDescriptor propertyDescriptor 
= propertyDescriptors[i];
                    
if ( propertyDescriptor != null ) 
                    {
                        String name 
= propertyDescriptor.getName();//属性名称
                        Method readMethod = propertyDescriptor.getReadMethod();//getXXX方法
                        Method writeMethod = propertyDescriptor.getWriteMethod();//setXXX方法
                        Class aType = propertyDescriptor.getPropertyType();//属性类型
                        if ( readMethod != null ) {
                            readMethods.put( name, readMethod );
//保存到getXXX集合
                        }
                        
if ( writeMethod != null ) {
                            writeMethods.put( name, writeMethod );
//保存到setXXX集合
                        }
                        types.put( name, aType );
//保存属性类型
                    }
                }
            }
        }
        
catch ( IntrospectionException e ) {
            logWarn(  e );
        }
    }

    
protected static class MyMapEntry extends AbstractMapEntry 
    {
//BeanMap使用的Map entry        
        private BeanMap owner;//所属的Map
       
        
protected MyMapEntry( BeanMap owner, Object key, Object value ) {
            
super( key, value );
            
this.owner = owner;
        }

        
public Object setValue(Object value) {
            Object key 
= getKey();
            Object oldValue 
= owner.get( key );

            owner.put( key, value );
            Object newValue 
= owner.get( key );
            
super.setValue( newValue );
            
return oldValue;
        }
    }

    
protected Object[] createWriteMethodArguments( Method method, Object value ) throws IllegalAccessException, ClassCastException 
    {            
        
try 
        {
            
if ( value != null ) 
            {
                Class[] types 
= method.getParameterTypes();//setXXX方法的参数类型
                if ( types != null && types.length > 0 ) 
                {
                    Class paramType 
= types[0];
                    
if ( ! paramType.isAssignableFrom( value.getClass() ) ) 
                    {
                        value 
= convertType( paramType, value );//把新参数转换为setXXX方法的参数类型
                    }
                }
            }
            Object[] answer 
= { value };
            
return answer;
        }
        
catch ( InvocationTargetException e ) {
            logInfo( e );
            
throw new IllegalArgumentException( e.getMessage() );
        }
        
catch ( InstantiationException e ) {
            logInfo( e );
            
throw new IllegalArgumentException( e.getMessage() );
        }
    }

    
protected Object convertType( Class newType, Object value ) 
        
throws InstantiationException, IllegalAccessException, IllegalArgumentException, InvocationTargetException {
        
        
// try call constructor
        Class[] types = { value.getClass() };
        
try {//尝试用带一个参数的构造函数进行转换
            Constructor constructor = newType.getConstructor( types );        
            Object[] arguments 
= { value };
            
return constructor.newInstance( arguments );
        }
        
catch ( NoSuchMethodException e ) {
            
// try using the transformers
            Transformer transformer = getTypeTransformer( newType );//获取可用的transformer
            if ( transformer != null ) {
                
return transformer.transform( value );//转换类型
            }
            
return value;
        }
    }

    
protected Transformer getTypeTransformer( Class aType ) {
        
return (Transformer) defaultTransformers.get( aType );
    }

}

 

posted on 2008-12-20 14:16  Phinecos(洞庭散人)  阅读(1405)  评论(0编辑  收藏  举报

导航