5

我需要将对象添加到列表(具有List语义),同时保持列表中的所有对象唯一。我认为LinkedHashSet可以,但“重新插入”子句打破了这一点:

LinkedHashSet<String>list = new LinkedHashSet<String>();
list.add("a");
list.add("b");
list.add("c");
list.add("a");
list.add("a");
System.out.println (list);

上面的输出是:[a, b, c],不是[b, c, a]我想要的。

Java中是否有任何此类数据结构可以处理这种情况?

4

3 回答 3

8

尝试

    Set<String> set = Collections.newSetFromMap(new LinkedHashMap<String, Boolean>(16, 0.75f, true));
    set.add("a");
    set.add("b");
    set.add("c");
    set.add("a");
    set.add("a");
    System.out.println(set);

输出

[b, c, a]
于 2013-01-23T09:53:52.300 回答
3

我不认为有一个开箱即用的数据结构可以做你想要的,因为它看起来有点奇怪。我建议您围绕 LinkedHashSet 创建一个包装器,当您尝试重新插入它并再次插入它时,它会弹出该元素。

于 2013-01-23T09:46:20.570 回答
2

实际上,JDK 库提供了一个开箱即用的数据结构。如果您查看此LinkedHashMap构造函数:

/**
 * Constructs an empty <tt>LinkedHashMap</tt> instance with the
 * specified initial capacity, load factor and ordering mode.
 *
 * @param  initialCapacity the initial capacity
 * @param  loadFactor      the load factor
 * @param  accessOrder     the ordering mode - <tt>true</tt> for
 *         access-order, <tt>false</tt> for insertion-order
 * @throws IllegalArgumentException if the initial capacity is negative
 *         or the load factor is nonpositive
 */
public LinkedHashMap(int initialCapacity,
                     float loadFactor,
                     boolean accessOrder) {
    super(initialCapacity, loadFactor);
    this.accessOrder = accessOrder;
}

有一个额外的参数accessOrder。基于此,新添加的对象将被移动到列表的末尾 ( accessOrder - true) 或保留在旧位置 ( accessOrder - false)。

为了创建Set具有这些特性的 a,您需要使用以下工厂方法java.util.CollectionsnewSetFromMap(LinkedHashMap(initialCapacity, loadFactor, accessOrder))

请记住,该accessOrder属性负责与给定元素的所有交互 - 如果您调用它getHashMap它也会重新排序(无论如何这不应该影响您,因为Set接口不会get在 Wrapped 上公开方法HashMap,只是说) .

于 2013-01-23T10:14:51.027 回答