在TreeSet中有一个名为contains的方法,如果元素在集合中,则返回true . 我假设此方法使用二进制搜索,并不按升序迭代所有元素 . 我对吗?
我有一个TreeSet,它包含一个类的对象,该类使用两个String实例变量来区分它与同一个类的其他对象 . 我希望能够通过比较两个实例变量(当然使用get方法)和另外两个String变量来创建一个搜索TreeSet的方法,如果它们相等,则返回该元素 . 如果实例变量小于转到右子树中的第一个元素,或者如果它们在左子树中搜索更大等等,有没有办法做到这一点?
我知道我可以将对象存储在ArrayList中并使用二进制搜索来查找对象,但这不会像搜索TreeSet那么快 .
5 回答
您可以将对象存储在
TreeMap<Foo, Foo>
或TreeMap<FooKey, Foo>
中(如果每次要搜索时都无法轻松创建新的实际Foo
),而不是使用TreeSet
.Set
s并不是真正用于查找的 .对于
FooKey
示例,FooKey
将是一个简单的不可变类,它只包含两个String
并且是Comparable
. 找到两个String
的Foo
的值将是treeMap.get(new FooKey(firstString, secondString))
的简单问题 . 这当然使用您想要查找值的树遍历 .做你想要的 .
您应该在对象上实现Comparable,或者在构造TreeSet时创建一个单独的Comparator类 . 这允许您插入自定义条目比较逻辑,并让TreeSet执行其优化的存储/搜索事物 .
我想知道的一件事是你为什么要搜索一个有序的集合?如果您希望能够按顺序迭代以及快速查找,则可以将对象存储在两个单独的数据结构中 . 一个像你的
SortedSet<Foo>
,然后也是一个类似于ColinD提到的HashMap<FooKey,Foo>
. 然后在TreeMap上获得常量时间查找而不是log(n) . 您必须写入两个结构的写入惩罚,以及具有两个数据结构的内存资源损失,但您已完全优化了对数据的访问 .此外,如果内存资源受到约束,并且您的字符串实际上是对象的区别,那么您可以在对象
Foo
上实现hashcode()
和equals()
然后只将它们用作键和值(如HashMap<Foo,Foo>
. 警告那就是你必须构造一个Foo
来调用getter .你得到了关于使用可比较/比较器的答案,但我想我会补充说你是对的,contains()进行二进制搜索,尽管你不需要知道这些细节