JDKのJava Bean内省メカニズム

4816 ワード

JDKのJava Bean内省メカニズム
JDK仕様リスト(https://www.cnblogs.com/binarylei/p/10200503.html)
JavaBeanは特別なJavaクラスであり、主にデータ情報を伝達するために用いられる。このようなJavaクラスの方法は主にプライベートフィールドにアクセスするために用いられ、方法名はある命名規則に適合する。
一、JavaBean
1.1 JavaBean命名ルール
  • JavaBeanクラスの方法は、setまたはgetプレフィックスを除いて、残りの部分は属性名であり、残りの部分の2番目の文字が小文字であれば、残りの部分のイニシャルを小さくする。getAge/setAge-->age gettime-->time setTime->time
  • プレフィクスが除去され、残りの部分の2番目の文字が大文字である場合、すべての大文字getCPU

  • 1.2内省とは何ですか?
    Java内省では主にJavaBeanを操作するために使われているので、クラスがJavaBeanの条件を満たしている場合は、内省的な方法でJavaBeanのフィールド値を取得して操作することができます。内部省はJavaBeanを操作するAPIを提供しています。
    Javaには、ある属性にアクセスするためのAPIのセットが提供されています。これらのAPIを通じて、このルールを知る必要がなく、これらのAPIは、パッケージjava.beansに格納されています。一般的な方法は、IntropspectorのgetBenInfo方法によって、あるオブジェクトのBeanInfo情報を取得し、BenInfoを通じて属性の記述器を取得します。(PropertyDescriptor)この属性記述器により、ある属性に対応するgetter/setter方法を取得し、反射機構によりこれらの方法を呼び出すことができます。
    二、JDK内省機構
    2.1 Intropector類
    Intropectorは、このクラスはjava.beansパッケージにあり、このクラスの方法は静的で、直接にクラス名を使って呼び出すことができます。
    //    beanClass         BeanInfo
    BeanInfo getBeanInfo(Class>beanClass)
    
    //    beanClass         stopClass   BeanInfo 
    BeanInfo getBeanInfo(Class> beanClass, Class> stopClass)
    Intropectorのget BeanInfoを使ってJavaBean類のBeanInfoオブジェクトを取得することができます。BenInfoには三つのよく使われている属性があります。
    // bean   
    BeanDescriptor beanDescriptor = beanInfo.getBeanDescriptor();
    //     
    PropertyDescriptor[] propertyDescriptors = beanInfo.getPropertyDescriptors();
    //     
    MethodDescriptor[] methodDescriptors = beanInfo.getMethodDescriptors();
    2.2 PropertyDescriptor類
    このクラスはjava.beansカバンの中にあります。
    @Test
    public void test() throws Exception {
        PropertyDescriptor pd = new PropertyDescriptor("id", User.class);
        System.out.println(pd.getName());
    }
    2.3 ProptyEditor類
    SpringではPropertyEditorを用いてJavaBeanに属性を注入します。
    @Test
    public void test1() throws Exception {
        User user = new User();
    
        PropertyDescriptor propertyDescriptor = new new PropertyDescriptor("id", User.class);
        propertyDescriptor.setPropertyEditorClass(IntPropertyEditor.class);
        PropertyEditor propertyEditor = propertyDescriptor.createPropertyEditor(user);
    
        propertyEditor.setAsText("99");
        Method writeMethod = propertyDescriptor.getWriteMethod();
        writeMethod.invoke(user, propertyEditor.getValue());
    
        System.out.println(user);
    }
    
    @Test
    public void test2() throws Exception {
        User user = new User();
    
        PropertyDescriptor propertyDescriptor = new new PropertyDescriptor("id", User.class);
        propertyDescriptor.setPropertyEditorClass(IntPropertyEditor.class);
        PropertyEditor propertyEditor = propertyDescriptor.createPropertyEditor(user);
    
        //    evt       propertyEditor   
        propertyEditor.addPropertyChangeListener(evt -> {
            PropertyEditor source = (PropertyEditor) evt.getSource();
            Method writeMethod = propertyDescriptor.getWriteMethod();
            writeMethod.invoke(user, source.getValue());
        });
        propertyEditor.setAsText("99");
        System.out.println(user);
    }
    
    // JDK    PropertyEditor   
    public static class IntPropertyEditor extends PropertyEditorSupport {
        @Override
        public void setAsText(String text) throws IllegalArgumentException {
            setValue(Integer.parseInt(text));
        }
    }
    三、Apache BeanUtilsツールバッグ
    ApacheはJavaBeanを操作するAPI(内省)のセットを開発しました。このツールは、commons-beanutilsのカバンの中で、コアクラスのBenUtils:
    setProperty(bean, name, value)
    copyProperties(target, source)
    Stringから8の基本データタイプへの変換が可能で、他の参照データタイプは登録コンバータCovertUtils.register(Coverter,Class)が必要です。
    BenUtilsを使って日付をフォーマットします。
    public static void main(String[] args) throws Exception {
            
        User user = new User();
        
        String name = "zhangsan";
        String birthday = "19801122";
        
        //        
        /*              
        ConvertUtils.register(new Converter() {
            
            public Object convert(Class beanClass, Object value) {
                String birthday = (String) value;
                SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMdd");
                try {
                    return sdf.parse(birthday);
                } catch (ParseException e) {
                    return null;
                }
            }
        }, Date.class);
        */
       
        DateConverter converter = new DateConverter();
        converter.setPatterns(new String[]{"yyyy-MM-dd","yyyyMMdd","MM/dd/yyyy"});
        ConvertUtils.register(converter, Date.class);
        
        BeanUtils.setProperty(user, "name", name);
        BeanUtils.setProperty(user, "birthday", birthday);
    
        System.out.println(user);  
    }
    参考:
  • 「JavaBean及び内省技術詳細」:https://www.cnblogs.com/yejiurui/archive/2012/10/06/2712693.html
  • 毎日少しずつメモしていきます。内容は重要ではないかもしれませんが、習慣は大切です。