Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/323.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java中无重复项和随机顺序的集合_Java_List_Set_Duplicates_Shuffle - Fatal编程技术网

Java中无重复项和随机顺序的集合

Java中无重复项和随机顺序的集合,java,list,set,duplicates,shuffle,Java,List,Set,Duplicates,Shuffle,看起来我既不能使用ArrayList也不能使用Set: Set-我可以使用Set避免重复,但没有shuffle选项/集合。shuffle(列表) ArrayList-我可以使用shuffle随机排列列表,但允许重复 我可以使用Set并将其转换为ArrayList(或者反过来),以避免重复。或者,在集合中循环以随机化项目。但我正在寻找更有效的方法。据我所知,集合是不有序的,所以显然不能对集合中的项目进行洗牌。要从列表中删除重复项,我发现如下:。您可以维护两个单独的集合,一个ArrayList和

看起来我既不能使用ArrayList也不能使用Set:

  • Set
    -我可以使用Set避免重复,但没有shuffle选项/
    集合。shuffle(列表)

  • ArrayList
    -我可以使用shuffle随机排列列表,但允许重复


我可以使用
Set
并将其转换为
ArrayList
(或者反过来),以避免重复。或者,在集合中循环以随机化项目。但我正在寻找更有效的方法。

据我所知,集合是不有序的,所以显然不能对集合中的项目进行洗牌。要从列表中删除重复项,我发现如下:。

您可以维护两个单独的集合,一个
ArrayList
和一个
HashSet
,并拒绝插入
HashSet
中存在的任何项

如果您关心封装,请将这两个集合包装在一个实现
List
的元对象中,并仔细记录重复元素的插入将被拒绝,即使
List
的通用合同没有规定


谈到此解决方案的成本,我认为,与普通的
ArrayList
相比,从时间角度来看,成本是完全可以忽略的:对
HashSet
s的大多数操作的成本分摊为O(1),即查找和插入。另一方面,您的内存使用率将是原来的两倍(或更多,具体取决于
HashSet
加载因子)。

使用最少的代码和最优雅的方式,您可以执行以下操作:

 public void testFoo() {
    Set<Integer> s = new TreeSet<Integer>();

    s.add(2);
    s.add(1);
    s.add(3);

    Collections.shuffle(Arrays.asList(s.toArray()));
}
public void testFoo(){
Set s=新树集();
s、 增加(2);
s、 增加(1);
s、 增加(3);
Collections.shuffle(Arrays.asList(s.toArray());
}
但这不是很有效,您可以使用数组和哈希函数将元素放置在数组中所需的位置,并在放置它们之前检查它们是否已经存在,这将在O(n)时间内工作,因此非常好,但需要更多的代码和对哈希函数的一些注意。

  • 可以使用映射避免重复,然后使用Map.entrySet()和无序排列ArrayList

您实际上可以使用“有序集”,例如树集。为了得到一个随机顺序,不要插入实际的项目,而是插入一个具有随机权重的包装器,并使用相应的比较器。但是,重新洗牌需要更新所有包装器权重。

您可以在添加项目之前检查项目是否已在ArrayList中:myList.contains(myItem);这个检查应该只有O(n)。更有效的东西>你这么说是因为你(a)尝试过,并且(b)通过适当的基准测试得出结论,这是你应用程序中的一个重要瓶颈吗?如果不是,请不要过早地优化和编写阅读最清楚的版本(可能转换为arraylist)。根据您对我的答案的评论,您的解决方案可能是最好的。但我要提到O(1)重复检查,它有点争议。在某些情况下,哈希集中的插入可能需要O(n)。但是我添加了它。您也可以实现Set,并创建一个迭代器,以随机顺序返回元素。@owlstead:我明白了,但这会破坏集合。shuffle()和客户端可能依赖它。这取决于整个场景。这是一个很好的观点gd1,在不能够在专有的
实现上使用
Collections.shuffle()
的情况下实现这一点可能很棘手。