【问题标题】:Iterating over a custom hashtable迭代自定义哈希表
【发布时间】:2018-08-23 03:41:12
【问题描述】:

我在 java 中有一个自定义的哈希表实现。

public class HashSet<T> implements HashTableInterface<T> {

private static int DEFAULT_ARRAY_SIZE = 10;

private T[] items;

public HashSet() {
    final T[] items = (T[]) new Object[DEFAULT_ARRAY_SIZE];
    this.items = items;
}

@Override
public boolean add(T item) {
    int index = getIndex(item);
    do {
        if (items[index] != null) {
            index = (index + 1) % DEFAULT_ARRAY_SIZE;
        } else {
            items[index] = item;
            break;
        }
    } while (index != getIndex(item));

    return true;
}

@Override
public boolean remove(T item) {
    if (contains(item)) {
        items[getIndex(item)] = null;
        return true;
    } else {
        return false;
    }
}

@Override
public boolean contains(T item) {
    T itemArray = items[getIndex(item)];
    if (item.equals(itemArray)) {
        return true;
    } else {
        int index = (getIndex(item) + 1) % DEFAULT_ARRAY_SIZE;
        do {
            if (items[index] != null) {
                if (items[index].equals(item)) {
                    return true;
                } else {
                    index = (index + 1) % DEFAULT_ARRAY_SIZE;
                }
            } else {
                break;
            }
        } while (index != getIndex(item));
    }
    return items[getIndex(item)] != null;
}

@Override
public int getIndex(T item) {
    return item.hashCode() % DEFAULT_ARRAY_SIZE;
}

@Override
public int size() {
    int count = 0;
    for (T item : items) {
        if (item != null) {
            count++;
        }
    }
    return count;
}

@Override
public String toString() {
    return items.toString();
}}

在我的 add 方法中,我想检查存储项目的位置是否空闲,如果不是,它应该转到下一个索引。直到它找到一个空的地方。

我的代码有效,但我认为,可能有更好的方法来做到这一点。

public boolean add(T item) {
    int index = getIndex(item);
    do {
        if (items[index] != null) {
            index = (index + 1) % DEFAULT_ARRAY_SIZE;
        } else {
            items[index] = item;
            break;
        }
    } while (index != getIndex(item));

    return true;
}

我在 contains 方法中遇到了同样的问题

public boolean contains(T item) {
    T itemArray = items[getIndex(item)];
    if (item.equals(itemArray)) {
        return true;
    } else {
        int index = (getIndex(item) + 1) % DEFAULT_ARRAY_SIZE;
        do {
            if (items[index] != null) {
                if (items[index].equals(item)) {
                    return true;
                } else {
                    index = (index + 1) % DEFAULT_ARRAY_SIZE;
                }
            } else {
                break;
            }
        } while (index != getIndex(item));
    }
    return items[getIndex(item)] != null;
}

【问题讨论】:

  • 你的班级不是一个集合。当遇到“重复”项目时,它会覆盖其内容中的另一个项目,并保留原始项目和重复项目。
  • 当一个重复项,具有相同的哈希值但不同的值将被添加时,它应该添加它们。但就在下一个空闲的地方。
  • 您的删除方法有问题,将删除与您实际要删除的元素具有相同哈希码的第一个条目。此外,它也使得无法再次找到其他元素。
  • @Fabian,然后正如我所说,这个类不是一个集合,因为添加一个副本到集合没有任何作用,而添加到您的数据结构中会替换一个完全不相关的项目。
  • @kutschkem 是的,我还在开发中。

标签: java loops iterator iteration hashtable


【解决方案1】:

有很多不同的方法来避免碰撞,你所做的就是所谓的“线性探测”。

还有(参考here

二次探测

双重哈希

以及使用链表来冲突值的方案。

所有这些都有不同的权衡,您应该了解这些权衡以做出明智的决定。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-07-29
    • 2010-10-22
    • 1970-01-01
    • 1970-01-01
    • 2011-02-28
    • 2014-12-15
    • 2017-09-02
    • 1970-01-01
    相关资源
    最近更新 更多