zoukankan      html  css  js  c++  java
  • Mybatis框架基础支持层——反射工具箱之实体属性Property工具集(6)

    本篇主要介绍mybatis反射工具中用到的三个属性工具类:PropertyTokenizer、PropertyNamer、PropertyCopier。

    PropertyTokenizer

    主要用来解析Mybatis使用过程中遇到的类似"order[0].items[0].name"这种由"."和"[ ]"组成的表达式:

    public class PropertyTokenizer implements Iterator<PropertyTokenizer> {
    
        /** ________________________
         * |order[0]|.items[0].name|
         * —————————————————————————
         *
         * 第一级表达式:name=order;indexName=order[0];index=0;children=item[0].name
         */
        /**
         * 当前表达式的名称
         */
        private String name;
        /**
         * 当前表达式的索引名
         */
        private String indexedName;
        /**
         * 当前表达式的索引
         */
        private String index;
        /**
         * 子表达式
         */
        private String children;
    
        /**
         * 初始化上述属性
         */
        public PropertyTokenizer(String fullname) {
            int delim = fullname.indexOf('.');
            if (delim > -1) {
                name = fullname.substring(0, delim);
                children = fullname.substring(delim + 1);
            } else {
                name = fullname;
                children = null;
            }
            indexedName = name;
            delim = name.indexOf('[');
            if (delim > -1) {
                index = name.substring(delim + 1, name.length() - 1);
                name = name.substring(0, delim);
            }
        }
    
        public String getName() {
            return name;
        }
    
        public String getIndex() {
            return index;
        }
    
        public String getIndexedName() {
            return indexedName;
        }
    
        public String getChildren() {
            return children;
        }
    
        @Override
        public boolean hasNext() {
            return children != null;
        }
    
        @Override
        public PropertyTokenizer next() {
            return new PropertyTokenizer(children);
        }
    
        @Override
        public void remove() {
            throw new UnsupportedOperationException("Remove is not supported, as it has no meaning in the context of properties.");
        }
    }

    PropertyNamer

    主要是用于实体类中getter、setter方法与相应属性的名称转换和相应的一些检测判断操作:

    public final class PropertyNamer {
    
        private PropertyNamer() {
            // Prevent Instantiation of Static Class
        }
    
        /**
         * get/set方法名转换为相应的属性名称
         */
        public static String methodToProperty(String name) {
            if (name.startsWith("is")) {
                name = name.substring(2);
            } else if (name.startsWith("get") || name.startsWith("set")) {
                name = name.substring(3);
            } else {
                throw new ReflectionException("Error parsing property name '" + name + "'.  Didn't start with 'is', 'get' or 'set'.");
            }
    
            if (name.length() == 1 || (name.length() > 1 && !Character.isUpperCase(name.charAt(1)))) {
                name = name.substring(0, 1).toLowerCase(Locale.ENGLISH) + name.substring(1);
            }
    
            return name;
        }
    
        /**
         * 检测方法名是否get、set方法
         */
        public static boolean isProperty(String name) {
            return name.startsWith("get") || name.startsWith("set") || name.startsWith("is");
        }
    
        /**
         * 检测方法名是否get方法
         */
        public static boolean isGetter(String name) {
            return name.startsWith("get") || name.startsWith("is");
        }
    
        /**
         * 检测方法名是否get方法
         */
        public static boolean isSetter(String name) {
            return name.startsWith("set");
        }
    }

    PropertyCopier

    主要用于相同类型的两个对象之间进行属性值的拷贝:

    public final class PropertyCopier {
    
        private PropertyCopier() {
            // Prevent Instantiation of Static Class
        }
    
        public static void copyBeanProperties(Class<?> type, Object sourceBean, Object destinationBean) {
            Class<?> parent = type;
            while (parent != null) {
                /**
                 * 获取到parent中所有被声明的字段,包括public、protected、default、private修饰的,除了
                 * 继承父类的字段
                 */
                final Field[] fields = parent.getDeclaredFields();
                for (Field field : fields) {
                    try {
                        field.setAccessible(true);
                        /**
                         *  将sourceBean的属性值设置到destinationBean中
                * set方法也不会将所有的属性值复制,有限制,具体限制可查看set源码
    */ field.set(destinationBean, field.get(sourceBean)); } catch (Exception e) { // Nothing useful to do, will only fail on final fields, which will be ignored. } } parent = parent.getSuperclass(); } } }
  • 相关阅读:
    Eclipse启动不了
    第三章Hibernate关联映射
    System Generator简介
    Chipscope使用
    总线及数据传输技术【待完善】
    多相滤波器
    notepad++与ISE/Vivado关联
    常用IP核
    〖Linux〗Qt+gsoap开发客户端程序,服务端地址设定的字符串转换处理
    〖Android〗OK6410a的Android HAL层代码编写笔记
  • 原文地址:https://www.cnblogs.com/wly1-6/p/10313223.html
Copyright © 2011-2022 走看看