我一直喜欢树木,它们很好,O(n*log(n))而且它们整洁.然而,我所知道的每一位软件工程师都有针对性地问我为什么会使用TreeSet.从CS背景来看,我认为你所使用的并不重要,而且我不想乱用哈希函数和桶(在这种情况下Java).
在这情况下,我应该使用HashSet过TreeSet?
我有一个使用Comparable <>定义'自然排序顺序'的对象.这些存储在TreeSet中.
除了删除和重新添加对象之外,还有另一种方法可以在更新用于定义排序顺序的成员时更新排序吗?
我今天接受了采访,接受采访的人对他的陈述感到困惑,询问是否可能TreeSet等于HashSet但不HashSet等于TreeSet。我说“不”,但据他说,答案是“是”。
怎么可能?
在使用树集时,我发现了非常奇特的行为.根据我的理解,这个程序应该打印两个相同的行:
public class TestSet {
static void test(String... args) {
Set<String> s = new TreeSet<String>(String.CASE_INSENSITIVE_ORDER);
s.addAll(Arrays.asList("a", "b"));
s.removeAll(Arrays.asList(args));
System.out.println(s);
}
public static void main(String[] args) {
test("A");
test("A", "C");
}
}
Run Code Online (Sandbox Code Playgroud)
但奇怪的是它打印:
[b]
[a, b]
Run Code Online (Sandbox Code Playgroud)
为什么树集会表现得像这样?
这是我用于Java 5.0的一段代码
TreeSet<Integer> treeSetObj = new TreeSet<Integer>( Collections.reverseOrder() ) ;
Run Code Online (Sandbox Code Playgroud)
Collections.reverseOrder()用于获取比较器,以反转元素的存储和迭代方式.
有更优化的方式吗?
我正在使用a TreeSet<Integer>,我只是想在集合中找到数字的索引.有没有一种很好的方法来实际使用二叉树的O(log(n))复杂度?
(如果没有,我该怎么做,有谁知道为什么不呢?我很好奇为什么这样的类会被包含在Java中而没有类似搜索功能的东西.)
如果我想检索和更新存储在TreeSet中的对象,该怎么办?
我问的原因是,我希望能够维护一些能够存储学生的数据结构.我希望它被排序(按成绩 - 这是学生的实例变量),并且 - 即使在我更新一个(或多个)成绩之后,它也需要保持排序.
因此,在简要查看了Java的集合之后,我决定使用TreeSet并设置一个比较器,按比例对两个学生进行比较.问题是,我刚发现TreeSet没有get()方法!
任何帮助和建议将不胜感激.
也许我没有使用正确的数据结构.我需要使用一个集合,但也想要有效地返回第k个最小元素.可以在Java中使用TreeSet吗?似乎没有TreeSet的内置方法来执行此操作.
请帮我.
同时使用 Java 8 和 Java 11,请考虑以下TreeSet带有String::compareToIgnoreCase比较器的内容:
final Set<String> languages = new TreeSet<>(String::compareToIgnoreCase);
languages.add("java");
languages.add("c++");
languages.add("python");
System.out.println(languages); // [c++, java, python]
Run Code Online (Sandbox Code Playgroud)
当我尝试删除 中存在的确切元素时TreeSet,它起作用了:所有指定的元素都被删除:
languages.removeAll(Arrays.asList("PYTHON", "C++"));
System.out.println(languages); // [java]
Run Code Online (Sandbox Code Playgroud)
但是,如果我尝试删除而不是 中存在的更多TreeSet,则调用根本不会删除任何内容(这不是后续调用,而是调用而不是上面的代码段):
languages.removeAll(Arrays.asList("PYTHON", "C++", "LISP"));
System.out.println(languages); // [c++, java, python]
Run Code Online (Sandbox Code Playgroud)
我究竟做错了什么?为什么会这样?
编辑:String::compareToIgnoreCase是一个有效的比较器:
(l, r) -> l.compareToIgnoreCase(r)
Run Code Online (Sandbox Code Playgroud) 我有一个包含> 100k对象的TreeSet.我有另一种方法,需要ArrayList作为参数.
有没有办法在不迭代整个TreeSet然后手动将每个对象添加到ArrayList的情况下完成此操作?