文章详情

  • 游戏榜单
  • 软件榜单
关闭导航
热搜榜
热门下载
热门标签
php爱好者> php文档>比较器:根据属性来比较两个对象大小

比较器:根据属性来比较两个对象大小

时间:2010-05-25  来源:夏德虎

比较器:根据属性来比较两个对象大小

package com.zte.frame.util;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.Comparator;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
/**
 * 比较器:根据属性来比较两个对象大小;<br>
 * 实现机制:反射get方法,获取属性值,再调用属性的compareTo方法比较大小<br>
 * 1.对属性类型的要求:实现Comparable接口,具体实现了compareTo方法的
 * 合法类型有String,Date,Integer,Long,Double ...<br>
 * 2.对比较的对象的要求,要比较的属性实现了get方法,且严格按照驼峰式命名方法实现
 * 应用实例:<br>
 * <code>
 *         List<OutBankBookPageBean> lst = new ArrayList<OutBankBookPageBean>;<br>
 *      //ouName是OutBankBookPageBean的一个属性名,CommonByAttrComparator.asc升序排列<br>
 *      CommonByAttrComparator comparator = new CommonByAttrComparator("ouName",CommonByAttrComparator.asc)<br>
 *        Collections.sort(resultLst, comparator);<br>
 * </code>
 *
 * @author xiadehu
 * @version 1.0 13/18/2009
 *
 */
public class CommonByAttrComparator implements Comparator{
    
    private Log log = LogFactory.getLog(getClass());

    /*
     * 升序排列
     */
    public static final int asc=0;
    /*
     * 降序排列
     */
    public static final int desc = 1;
    /*
     * 排序类型,升序/降序
     */
    private int sortType=0;
    /*
     * 要排序的属性名
     */
    private String attrName = null;
    /*
     * get常量
     */
    private String get = "get";
    /*
     * 科学计数法正则表达式,诸如"1,222,002.00"类的字符串
     */
    private String DECIMAL_PATTERN = "-?(\\d{1,3},{1})*\\d{1,3}\\.{1}\\d{2}";
    /**
     * 构造函数
     * @param attrName
     * @param sortType
     */
    public CommonByAttrComparator(String attrName,int sortType){
        this.sortType=sortType;
        this.attrName=attrName;
    }
    /**
     * 通过反射实现比较方法
     */
    @SuppressWarnings("unchecked")
    public int compare(Object src, Object desc) {
        if(src==desc){
            return 0;
        }
        if(src==null){
            return -1;
        }
        if(desc==null){
            return 1;
        }
        try {
            //获取get方法
            Method mSrc = src.getClass().getMethod(getMethodName());
            Method mDesc = desc.getClass().getMethod(getMethodName());
            Comparable srcValue = (Comparable) mSrc.invoke(src, new Object[]{});
            Comparable descValue = (Comparable) mDesc.invoke(desc, new Object[]{});
           
            //判断通过get方法获取的值是否为空
            if(srcValue==descValue){
                return 0;
            }
            if(srcValue==null){
                return -1;
            }
            if(descValue==null){
                return 1;
            }
           
            //针对字符串作的增强排序,如果是金额类型字符串则按照金额大小排序
            int result = adviceCompareNumString(srcValue,descValue);
            if(Integer.MIN_VALUE!=result){
                return result;
            }
           
            //调用compareTo方法,获取比较结果
            int compareValue = srcValue.compareTo(descValue);
            //如果为asc排序,则直接返回比较值,否则取反结果并返回
            return sortType==asc?compareValue:reverseValue(compareValue);
        } catch (SecurityException e) {
            log.error(e.getMessage(),e);
        } catch (NoSuchMethodException e) {
            log.error(e.getMessage(),e);
        } catch (IllegalArgumentException e) {
            log.error(e.getMessage(),e);
        } catch (IllegalAccessException e) {
            log.error(e.getMessage(),e);
        } catch (InvocationTargetException e) {
            log.error(e.getMessage(),e);
        }
        return 0;
    }
   
    /**
     *
     * 方法注释: 针对金额字符串作的增强排序,如果是金额类型字符串则按照金额大小排序 .<br>
     * <b>xiadehu 2009-8-20 下午06:00:56</b>
     * @param srcValue
     * @param descValue
     * @return
     */
    private int adviceCompareNumString(Comparable srcValue, Comparable descValue) {
        try {
            if(srcValue instanceof String && descValue instanceof String){//如果srcValue和descValue均为String
                String src = (String) srcValue;
                String desc = (String) descValue;
                if(src.matches(DECIMAL_PATTERN)&&desc.matches(DECIMAL_PATTERN)){//如果src和desc均为科学计数式字符串
                    Double srcD = Double.parseDouble(src);
                    Double descD = Double.parseDouble(desc);
                    int value = srcD.compareTo(descD);
                    return sortType==asc?value:reverseValue(value);
                }
            }
        } catch (NumberFormatException e) {
            log.info("字符串长度过长,未采取增强金额比较法进行比较");
        }
        return Integer.MIN_VALUE;
    }
    /**
     *
     * 方法注释: 取反比较结果 .<br>
     * <b>xiadehu 2009-8-13 上午10:38:36</b>
     * @param value
     * @return
     */
    private int reverseValue(int value){
        return (-1)*value;
    }
   
    /**
     *
     * 方法注释: 通过属性获取get方法名 .<br>
     * <b>xiadehu 2009-8-13 上午10:38:54</b>
     * @return
     */
    private String getMethodName(){
        if(this.attrName==null || attrName.trim().length()==0){
            throw new RuntimeException("比较器内部错误,要比较的属性不能为null或空");
        }
        return get+attrName.substring(0, 1).toUpperCase().concat(attrName.substring(1,attrName.length()));
    }
    public String getAttrName() {
        return attrName;
    }
    public void setAttrName(String attrName) {
        this.attrName = attrName;
    }
    public int getSortType() {
        return sortType;
    }
    public void setSortType(int sortType) {
        this.sortType = sortType;
    }
   
}
相关阅读 更多 +
排行榜 更多 +
辰域智控app

辰域智控app

系统工具 下载
网医联盟app

网医联盟app

运动健身 下载
汇丰汇选App

汇丰汇选App

金融理财 下载