繁体   English   中英

SparseBooleanArray.equals()无法按预期工作

[英]SparseBooleanArray.equals() not working as expected

在下面的代码中,我希望equals()返回true ,但事实并非如此。 我在这里错过了什么?

    SparseBooleanArray array_0 = new SparseBooleanArray();
    array_0.put(0, true);
    array_0.put(2, true);

    SparseBooleanArray array_1 = new SparseBooleanArray();
    array_1.put(0, true);
    array_1.put(2, true);

    boolean isEqual = array_0.equals(array_1); // is false instead of true

在调试器中查看这两个数组,它们对我来说似乎是一样的(它们有一个不同的shadow$_monitor_值,但我不知道应该是什么)。 toString()方法也为两者返回相同的字符串。

我正在尝试为将EnumSet转换为SparseBooleanArray的函数编写单元测试,但我无法手动创建相同的数组以将其与函数的返回值进行比较。


编辑

我还应该提一下, hasCode()也会返回不同的值,根据文档 ,它不应该返回。

查看源代码,对于SparseBooleanArraySparseIntArraySparseLongArraySparseArray ,都没有实现equalshashCode方法。 我会说这是一个关键的缺失功能,应该报告给谷歌。

无论如何,我使用这些实用方法已经有一段时间来解决这个问题了:

public static boolean equals(SparseArray arrayOne, SparseArray arrayTwo){
    if(arrayOne == arrayTwo){
        return true;
    } else if(arrayOne.size() != arrayTwo.size()){
        return false;
    }
    for(int i = 0; i < arrayOne.size(); i++){
        if(arrayOne.keyAt(i) != arrayTwo.keyAt(i)){
            return false;
        }
        final Object valueOne = arrayOne.valueAt(i);
        final Object valueTwo = arrayTwo.valueAt(i);
        if(valueOne != null && !valueOne.equals(valueTwo)){
            return false;
        } else if(valueTwo != null && !valueTwo.equals(valueOne)){
            return false;
        }
    }
    return true;
}

public static boolean equals(SparseBooleanArray arrayOne, SparseBooleanArray arrayTwo){
    if(arrayOne == arrayTwo){
        return true;
    } else if(arrayOne.size() != arrayTwo.size()){
        return false;
    }
    for(int i = 0; i < arrayOne.size(); i++){
        if(arrayOne.keyAt(i) != arrayTwo.keyAt(i)){
            return false;
        } else if(arrayOne.valueAt(i) != arrayTwo.valueAt(i)){
            return false;
        }
    }
    return true;
}

public static boolean equals(SparseIntArray arrayOne, SparseIntArray arrayTwo){
    if(arrayOne == arrayTwo){
        return true;
    } else if(arrayOne.size() != arrayTwo.size()){
        return false;
    }
    for(int i = 0; i < arrayOne.size(); i++){
        if(arrayOne.keyAt(i) != arrayTwo.keyAt(i)){
            return false;
        } else if(arrayOne.valueAt(i) != arrayTwo.valueAt(i)){
            return false;
        }
    }
    return true;
}

@RequiresApi(api = Build.VERSION_CODES.JELLY_BEAN_MR2)
public static boolean equals(SparseLongArray arrayOne, SparseLongArray arrayTwo){
    if(arrayOne == arrayTwo){
        return true;
    } else if(arrayOne.size() != arrayTwo.size()){
        return false;
    }
    for(int i = 0; i < arrayOne.size(); i++){
        if(arrayOne.keyAt(i) != arrayTwo.keyAt(i)){
            return false;
        } else if(arrayOne.valueAt(i) != arrayTwo.valueAt(i)){
            return false;
        }
    }
    return true;
}

但是,也可以(如注释中所述),并且可能更好,子类化SparseArray类并覆盖equalshashCode方法。

免责声明:我没有测试hashCodeequals下面提供的代码的实现,请自己编写一些测试以确保它正常工作。 #DontTrustTheInternet

public class SparseBooleanArray extends android.util.SparseBooleanArray {

    @Override
    public boolean equals(Object o) {
        if(!(o instanceof SparseBooleanArray)){
            return false;
        } else if(this == o){
            return true;
        }
        final SparseBooleanArray other = (SparseBooleanArray) o;
        if(size() != other.size()){
            return false;
        }
        for(int i = 0; i < size(); i++){
            if(keyAt(i) != other.keyAt(i)){
                return false;
            } else if(valueAt(i) != other.valueAt(i)){
                return false;
            }
        }
        return true;
    }

    @Override
    public int hashCode() {
        int result = 17;
        for(int i = 0; i < size(); i++){
            result = 31 * result + keyAt(i);
            result = 31 * result + (valueAt(i)?1:0);
        }
        return result;
    }
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM