Java Generic code

2022-09-03 00:52:01

我是泛型的新手。您可以看到我在知道 , , 的确切类型后重复了一些代码。我想编写用于比较筛选器值的通用代码。我可以写这样的东西valfilterSmallfilterGreatval

  private  <T> boolean  compareAgainstFilters(T val, T filterSmall, T filterGreat) {
    if (!(filterSmall != null && filterSmall <= val)) {
        return true;
    } 

    if (!(filterGreat != null && val <= filterGreat)) {
        return true;
    }
    return true;
}

但是在编译时,java不会知道运算符是否对类型有效。<=T

我不想重复代码,那么我该如何实现呢?

if (value != null) {
        switch (value.getClass().getName()) {
        case "java.lang.Long":
            Long filterSmall = (Long) filterSmaller;
            Long filterGreat = (Long) filterGreater;
            Long val = (Long) value;

            if (!(filterSmall != null && filterSmall <= val)) {
                return true;
            } 

            if (!(filterGreat != null && val <= filterGreat)) {
                return true;
            }
            break;

        case "java.lang.Float":
            Float filterSmallFloat = (Float) filterSmaller;
            Float filterGreatFloat = (Float) filterGreater;
            Float valFloat = (Float) value;

            if (!(filterSmallFloat != null && filterSmallFloat <= valFloat)) {
                return true;
            } 

            if (!(filterGreatFloat != null && valFloat <= filterGreatFloat)) {
                return true;
            }
        }
    }

答案 1

您可以使用该接口来比较数字,因为所有数字基元的包装类都实现了它:Comparable

  private  <T extends Comparable<T>> boolean  compareAgainstFilters(T val, T filterSmall, T filterGreat) {
    if (!(filterSmall != null && filterSmall.compareTo(val)<=0)) {
        return true;
    } 

    if (!(filterGreat != null && val.compareTo(filterGreat)<=0)) {
        return true;
    }
    return true;
}

<T extends Comparable<T>>限制可用作类型参数的类型,而不是 T。在这种情况下,需要他们来实现 。Comparable<T>


答案 2

不能在泛型方法中使用 或 运算符。通常,当变量的类型为 或 时,编译器会在编译代码中执行自动拆箱转换(以获取基元类型)后接受运算符。换句话说,<>FloatLong

filterSmall <= val

编译为:

filterSmall.longValue() <= val.longValue()

在泛型方法中,编译器无法应用取消装箱转换。执行比较的唯一方法是让类型参数扩展接口,并使用该方法。请注意,类型 等已经实现了此接口。ComparablecompareToFloatLong


推荐