在升序和降序中使用2个属性进行比较

时间:2016-07-01 16:09:06

标签: java sorting comparator

我有一个具有多个属性的对象,其中两个用户可以选择按顺序排列,两者都可以是升序,降序或两者都不是(正常),并且它们彼此独立。所以我的案例是:

案例1

  • propA - 正常
  • propB - 正常

案例2

  • propA - Asc
  • propB - 正常

案例3

  • propA - Desc
  • propB - 正常

你明白了。我使用Comparator执行此操作,到目前为止,当一个或两个值设置为Normal时,我能够对其进行排序。我不确定的部分是当我选择按两种方法排序时该怎么做。例如,如果我想按propA升序和propB降序排序,它应该看起来有点像这样

propA    propB
  A        Z
  A        D
  B        M
  B        A
  R        Q
  Z        Z
  Z        A

以下是我现在排序的方式

@Override
public int compare(Field lhs, Field rhs) {
    switch (growerSort) {
        case NORMAL:
            switch (fieldSort) {
                case NORMAL:
                    return ((Integer) lhs.getID()).compareTo(rhs.getID());
                case ASC:
                    return lhs.getPropB().toLowerCase().compareTo(rhs.getPropB().toLowerCase());
                default:
                    return rhs.getPropB().toLowerCase().compareTo(lhs.getPropB().toLowerCase());
            }
        case ASC:
            switch (fieldSort) {
                case NORMAL:
                    return lhs.getPropA().toLowerCase().compareTo(rhs.getPropA().toLowerCase());;
                case ASC:
                    return 0; // 0 used as placeholder
                default:
                    return 0; // 0 used as placeholder
            }
        default:
            switch (fieldSort) {
                case NORMAL:
                    return rhs.getPropA().toLowerCase().compareTo(lhs.getPropA().toLowerCase());
                case ASC:
                    return 0; // 0 used as placeholder
                default:
                    return 0; // 0 used as placeholder
            }
    }
}

如何使用两个不同的字段进行排序,每个字段都有自己的排序顺序?

2 个答案:

答案 0 :(得分:1)

我对你的Comparator感到有些困惑。要理解什么开关触发什么事件并不容易 但是我会描述标准程序。

您要比较的字段需要优先顺序。在上面的示例中,我假设首先必须按propA排序,然后按propB排序 然后,您首先按propA排序。如果它返回“等于”(),则您希望按下一个字段propB排序,等等。

让我举个例子:

@Override
public int compare(final Field lhs, final Field rhs) {
    int firstCompareValue = lhs.getPropA().compareTo(rhs.getPropA());

    if (firstCompareValue == 0) {
        // lhs and rhs are equals in propA, use propB
        int secondCompareValue = lhs.getPropB().compareTo(rhs.getPropB());
        return secondCompareValue;
    } else {
        return firstCompareValue;
    }
}

当然,如果您有多个字段,只要您指定了一个订单(例如,通过在您的属性字段上使用有序列表),您也可以执行此迭代。

现在你需要将你的开关添加到这个展示中:)我建议你做一个PropertyComparator

public final class PropertyComparator extends Comparator<Comparable<?>> {
    private final boolean mUseDscOrder = false;

    public void setUseDscOrder(final boolean useDscOrder) {
            mUseDscOrder = useDscOrder;
    }

    public int compare(final Comparable<?> o1, final Comparable<?> o2) {
            if (!mUseDscOrder) {
                    return o1.compareTo(o2);
            } else {
                    // Reverses the logic, results in DscOrder
                    return o2.compareTo(o1)
            }
    }
}

现在使用上面的Comparator

@Override
public int compare(final Field lhs, final Field rhs, final boolean firstUseDscOrder, final boolean secondUseDcsOrder) {
    PropertyComparator firstComparator = new PropertyComparator();
    firstComparator.setUseDscOrder(firstUseDscOrder);

    int firstCompareValue = firstComparator.compare(lhs.getPropA(), rhs.getPropA());

    if (firstCompareValue == 0) {
        // lhs and rhs are equals in propA, use propB

        PropertyComparator secondComparator = new PropertyComparator();
        secondComparator.setUseDscOrder(secondUseDscOrder);

        int secondCompareValue = secondComparator.compare(lhs.getPropB(), rhs.getPropB());
        return secondCompareValue;
    } else {
        return firstCompareValue;
    }
}

我没有测试过,但我认为你明白了这一点:)

答案 1 :(得分:0)

创建1个comparator,对“第一个字段”进行排序。如果第一个字段的值相等,则在“第二个字段”上排序。

if(object1.f1.equals(object2.f1)){

 object1.f2.compareTo(object2.f2);

} else {

  object1.f1.compareTo(object2.f1); 

}