将集合类型转换为 HashSet 和使用集合初始化 HashSet 之间有什么区别?

What is the difference between type casting a set to HashSet and initializing a HashSet with a set?

我想将集合 values(来自 Collectors.toSet())转换为 HashSet,这两者之间有什么区别,通常首选哪个?

HashSet<Integer> set = new HashSet<Integer>(values);
HashSet<Integer> set = (HashSet<Integer>) values;

我没有看到第二个选项使用得那么多,但是转换它不是比创建一个新对象更快吗?

如果原来的 Set 不是 HashSet,后者将抛出 ClassCastException

你不是在这里的任何地方施放一个集合。 Set 是一个接口,这意味着它不能被实例化(类 implement set can be instantiated)。这意味着您的变量 values 需要一个实现,例如哈希集。因此,选项二仅在已经实例化某种集合的情况下才有效,这会更慢(我认为你的意思更冗长)。像这样:

Set<Integer> = new HashSet<Integer> values;
HashSet<Integer> set = (HashSet<Integer>) values. 

很可能一开始就没有人会做这样的事情,坚持使用简单的老式哈希更有意义:

HashSet<Integer> set = new HashSet<Integer>();

您可能还认为没有像这样的实现也可以:

1 Set<Integer> values; 
2 HashSet<Integer> set = (HashSet<Integer>) values;

因为在第 1 行我们可以创建 Set 接口的变量(请记住没有实际对象)这一行没问题。但是如果没有实现,在第 2 行进行转换就没有意义了。

总而言之,这个问题从一开始就没有太大意义。在实际需要投射的地方投射。

主要区别在于 new 创建一个新对象,但类型转换不会。

考虑以下示例:

HashSet<Integer> one = ...

HashSet<Integer> two = new HashSet<Integer>(one);
HashSet<Integer> three = (HashSet<Integer>) one;

System.out.println(one == two);  // Prints false
System.out.println(one == three);  // Prints true

也就是说,onethree指的是同一个对象,但是two指的是不同的对象。

除了 == 的不同结果,您会发现 one 引用的集合的更新将通过 three 可见,而不是通过 two .


I don't see the second option used as much, but wouldn't it be faster to cast than creating a new object?

您看不到它使用太多的原因是因为第二个选项不会创建新对象!