[英]using TreeSet to sort without providing a Comparator to it
我知道java中的TreeSet
按升序自动对其元素进行排序,以保证顺序。
例如,如果我有一个随机的Date
对象数组,并将其复制到TreeSet
那么它将以有序的方式添加到TreeSet
中。
但是假设我有一个HashMap<String,Object>
的ArrayList
,而不是一个简单的Date
对象,格式如下。
arraylist的第一个价值,
{mydate = 32156464 , mystring = "abc", mystring2 = "xyz"}
hashmap的arraylist中的第二个值,
{mydate = 64687678 , mystring = "abdc", mystring2 = "xyzzz"}
hashmap的arraylist中的第3个值,
{mydate = 11233678 , mystring = "abxdc", mystring2 = "xyzppzz"}
现在,如果我想基于mydate
键对这个hashmap的arraylist进行排序,我必须在TreeSet
实例中创建一个新的比较器,如下所示,
public static Set<HashMap<String, Object>> mySet = new TreeSet<>(new Comparator<HashMap<String, Object>>() {
@Override
public int compare(HashMap<String, Object> o1, HashMap<String, Object> o2) {
return ((Date) o2.get(mydate)).compareTo((mydate) o1.get(DATE));
}
});
并且它会按照排序顺序将arraylist存储在TreeSet
中。 但我使用自定义Comparator
来实现这一目标。 如果我还在为它提供自定义Comparator
,那么在这种情况下使用TreeSet
对数据进行排序有什么意义呢?
如何在不使用TreeSet
的Comparator
新实例的情况下,根据date
值对HashMap
的ArrayList
进行排序?
如果我还在为它提供自定义Comparator,那么在这种情况下使用TreeSet对数据进行排序有什么意义呢?
因为它是TreeSet
代码,它保持排序。 您还没有提供任何为代码的- 所有你必须提供的是自定义比较。
如何在不使用TreeSet中的Comparator新实例的情况下,根据日期值对HashMap的ArrayList进行排序?
你不能,直接。 你可以写一个HashMap
的子类,它为自己实现了Comparable
,但这对我来说似乎有些奇怪。 例如:
public class SpecialMap extends HashMap<String, Object>
implements Comparable<SpecialMap> {
private final String key;
public SpecialMap(String key) {
this.key = key;
}
public int compareTo(SpecialMap other) {
// TODO: Null handling
Date thisDate = (Date) this.get(key);
Date otherDate = (Date) other.get(key);
return thisDate.compareTo(otherDate);
}
}
然后你可以有一个ArrayList<SpecialMap>
并对其进行排序。
但鉴于您必须提供与比较器基本相同的代码并将您的比较与地图类型绑定,我觉得最好只是坚持使用比较器。
如果你没有向TreeSet
提供Comparator
,那么它将依赖它的元素Comparable
来对它们进行排序。 如果它们不是Comparable
,那么将导致ClassCastException
。 TreeSet
javadocs解释:
基于TreeMap的NavigableSet实现。 元素按照其自然顺序排序 ,或者在创建时创建时提供的比较器 ,具体取决于使用的构造函数。
但是HashMap
类不是Comparable
,因此您必须提供自定义Comparator
以便TreeSet
知道您希望如何对它们进行排序。 如果没有Comparator
,您无法对HashMap
排序,无论它们是在TreeSet
还是在任何其他集合中。
在这种情况下使用TreeSet
有一些优点。 添加,查找和删除操作是O(log n)。 如果您为此使用ArrayList
,则添加和删除操作将为O(n),即使查找操作仍为O(log n)。
更多来自TreeSet
javadocs:
此实现为基本操作(添加,删除和包含)提供了有保证的log(n)时间成本。
您可以创建一个包含mydate,mystring,mystring2并实现Comparable接口的类,而不是使用HashMap。
但是,使用比较器是一种很好的做法,因为您将能够在运行时提供排序条件。
在TreeSet中使用比较器的关键是你没有编写代码来进行实际排序,你只需提供一种方法,根据比较规则确定哪个对象是第一个。 如果您不想创建比较器,则需要添加实现Comparable接口的集合对象。 要对ArrayList进行排序,请使用Collections.sort()。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.