在不使用 Java.util.* 方法的情况下覆盖 Java 中的 deepEquals() 方法

Override deepEquals() method in Java without using Java.util.* method

提问人:zixuan zhu 提问时间:11/27/2022 最后编辑:zixuan zhu 更新时间:11/27/2022 访问量:100

问:

我的文件中的方法有问题,但我无法弄清楚。 它也应该有意义。deepEqualsArrayDequeLinkedListArrayDeque

如何在不使用的情况下使deepEquals工作Java.util.* method


下面的代码是关于一个双端数组队列的,其中第一项被添加到数组的中间。 我删除了几种方法以进行简要查看。

package deque;

import java.util.Iterator;

public class ArrayDeque<T> implements Deque<T>, Iterable<T> {
    private T[] ts;
    private int size;

    private int stposition;
    private int firposition;
    private int lastposition;

    public ArrayDeque() {
        ts = (T[]) new Object[8];
        size = 0;
        stposition = Math.round(ts.length / 2);
        firposition = stposition;
        lastposition = stposition;
    }

    public T get(int i) {
        if (size < i | size == 0) {
            return null;
        }
        int pos = (firposition + i) % ts.length;
        return ts[pos];
    }

    public int size() {
        return size;
    }

    @Override
    public Iterator<T> iterator() {
        return new ArrayDequeIterator();
    }
    private class ArrayDequeIterator implements Iterator<T> {
        private int pos0 = firposition;
        public boolean hasNext() {
            if (size == 0) {
                return false;
            }
            if (pos0 == lastposition) {
                return true;
            }
            if (size > 1) {
                if (firposition < lastposition) {
                    if (pos0 < lastposition) {
                        return true;
                    }
                } else {
                    if (pos0 + 1 < ts.length) {
                        return true;
                    }
                }
                return false;
            }
            return false;
        }
        public T next() {
            T x = ts[pos0];
            pos0 = (pos0 + 1) % ts.length;
            return x;
        }
    }

    @Override
    public boolean equals(Object o) { // the equal method passed the tests but deepequal fail
        if (o == this) {
            return true;
        }
        if (o == null || this == null) {
            return false;
        }
        if (!(o instanceof Deque)) {
            return false;
        }
        Deque oll = (Deque) o;
        if (oll.size() != this.size()) {
            return false;
        }
        for (int i = 0; i < this.size(); i++) {
            Object a2 = oll.get(i);
            Object a1 = this.get(i);
            if (a1 == a2) {
                continue;
            }
            if (a2 == null) {
                return false;
            }
            if (a1.getClass() != a2.getClass()) {
                return false;
            }
            return deepEquals(a1, a2);
        }
        return true;
    }

    private boolean deepEquals(Object a1, Object a2) {
        boolean deq;
        if (a1 instanceof Deque) { 
        // maybe it's wrong here, I am not sure how to write this
            deq = a1.equals(a2);
        } else {
            if (a1 == a2) {
                return true;
            }
            return false;
        }
        return deq;
    }
}

我终于想通了。感谢所有的帮助。

它确实不需要另一种方法。
方法本身就足够了。
deepEqualequals

代码如下:
(1.我的界面中没有方法,所以我就用了方法。但我可以将它用于.感谢@knittl的建议。
2. 我认为在我的代码中很重要。我终于想通了...)。
iteratordequeget(i)this(!a1.equals(a2))

public boolean equals(Object o) {
        if (o == this) {
            return true;
        }
        if (o == null) {
            return false;
        }
        if (!(o instanceof Deque)) {
            return false;
        }
        Deque oll = (Deque) o;
        if (oll.size() != this.size()) {
            return false;
        }
        int i = 0;
        for (final Object a1 : this) {
            Object a2 = oll.get(i);
            i += 1;
            if (a1 == a2) {
                continue;
            }
            if (a2 == null) {
                return false;
            }
            if (a1.getClass() != a2.getClass()) {
                return false;
            }
            if (!a1.equals(a2)) {
                return false;
            }
        }
        return true;
    }
Java 数组 算法 比较 deepequals

评论

0赞 knittl 11/27/2022
this == null该检查是无用的,永远不会为空。但是你为什么需要?只需调用(或)您的对象即可。deep_equals方法不会在常规方法的基础上添加任何内容。thisdeepEqualsequalsObjects.equals(a, b)equals
0赞 zixuan zhu 11/27/2022
@knittl 谢谢你的建议。我会删除检查。因为测试需要我们自己覆盖方法,但我写的东西无法通过测试。如果自己写的方法能通过测试,没有单独有也没关系。this == nullequalsdeepEqualequaldeepEqualdeepEquals
0赞 zixuan zhu 11/27/2022
在这里,我首先尝试逐个比较对象和,以及每个对象中的项目。如果这两个对象中的一个项目是 or 或类似的东西,我想我需要首先调用以在这个项目本身中运行一个循环(调用)。我认为这两种方法都需要覆盖吗?我不确定。@user16320675othisArrayDequeLinkedListDequedeepEqualsequals

答:

1赞 knittl 11/27/2022 #1

您将希望 equals 方法比较列表中的每个项目是否相等。如果两个项不相等,则返回 false。请注意,按索引访问链表中的项是 O(n),这意味着 equals 方法具有二次运行时复杂度。使用迭代器来避免这种情况。

        // ...
        for (int i = 0; i < this.size(); i++) {
            Object a2 = oll.get(i);
            Object a1 = this.get(i);
            if (!Objects.equals(a1, a2)) {
              return false;
            }
        }
        return true;
    }

使用迭代器(为您提供线性运行时复杂性):

        // ...
        Iterator<Object> otherIterator = oll.iterator();
        for (final Object a1 : this) {
            // guaranteed to work, because both lists have the same size:
            final Object a2 = otherIterator.next();
            if (!Objects.equals(a1, a2)) {
              return false;
            }
        }
        return true;
    }

评论

0赞 zixuan zhu 11/27/2022
在我们的实现中,我们不允许使用 Java 内置的 LinkedList 数据结构(或来自 的任何数据结构)。我怎样才能在 Java 中实现?对不起,我没有在标题中说清楚。java.util.*Objects.equals(a1, a2)
0赞 knittl 11/27/2022
@zixuanzhu看一下实现并自己实现。从本质上讲,它执行空安全相等检查。