集合详解
集合是存放对象的引用的容器。
集合 = 数组/其他内存结构 + 可变长度 + 一堆方法 + 简单操作。
集合类型主要有3种:set、list和map。
| |
| |------>HashSet |
| |->Set-----|------>TreeSet |
| | |------>LinkedHashSet 自己了解 |
| | |
| Collection------| |------>ArrayList |
| |->List----|------>Vector 自己了解 |
| |------>LinkedList 自己了解 |
|_______________________________________________________________________________|
| |
| |------>HashMap |
| Map--------------------->Map----|------>TreeMap |
| |------>Hashtable 自己了解 |
1.Set list基本操作:Collection接口声明了Set接口、List接口的通用方法
list 有序可重复
set 无序
1.1boolean add(Object o);向集合中添加数据
1.2从集合中取数据
2.1list.get(i);//取list集合的i+1个对象
2.2 Iterator iterator(); //获取集合的迭代器(迭代器用来遍历集合);
1.3 获得集合长度
list.size();//获取长度
1.4 清空集合list.clear();// 删除集合中的所有对象引用,即不再持有这些对象的引用;
1.5 删除集合中某一个数据 remove(Obj) ;//从集合中删除一个对象的引用;
1.6 返回数组 Object[] toArray() 返回一个数组,该数组包含集合中的所有元素;
1.7判断在集合中是否持有特定对象的引用;contains(Obj)
2.集合存储多种类型的值
ArrayList<Object> list = new ArrayList<Object>();
list.add("23");
list.add(128);
3.遍历集合
Iterator接口:迭代器
hasNext()是否有下一个元素
next() 获取下一个元素
remove() 删除当前元素
例: Iterator it=list.iterator();
while(it.hasNext()){
Sytem.out.println(it.next());
}
4.HashSet
1).主要特点:不能储存相同的值,存储数据都是无序的。存储元素的顺序按照hashCode值
2). 按照哈希算法来存取集合中的对象,存取速度比较快。当向集合中加入一个对象时,HashSet会调用对象的hashCode()方法来获得哈希码,然后根据这个哈希码进一步计算出对象在集合中的存放位置。
---> 两个对象的值相同(equals()比较相同) ,那么这两个对象的hashCode一定相同。
---> 两个对象的hashCode相同,那么这两个对象的值不一定相同。
3).先 hashCode() && 后 equals() 同时满足这两个才被hashSet认为是同一个对象。
4),建立一个类Customer,给两个属性.name,age。
2,重写equals()方法,如果name相同age相同就返回true,else return false;
3,创建 HashSet集合,添加两个Customer对象(name,age相同);
4,打印集合长度--->考虑为啥 是 2 ?
5,从写hashCode方法(), return age;
6,再次打印 3 集合--->为何长度是1 ?
hashSet的底层实现依靠equals()和hashcode()方法。避免重复的规则:
先判断新元素与集合内已经有的旧元素的HashCode值
如果不同,说明是不同元素,添加到集合。
如果相同,再判断equals比较结果。返回true则相同元素;返回false则不同元素,添加到集合。
用hashSet存储时,如果没有重写hashCode和equals方法,判断重复比较的是地址值,
如果想通过内容比较元素是否相同,需要重写该元素类的hashcode与equals方法。
5.TreeSet:有序的集合,可以按照规定排序的集合。
1).自然排序:实现了Comparator接口,重写了compareTo(Object o)方法;(从小到大)
JDK类库中实现了Comparable接口的一些类的排序方式:
Byte, Short, Integer, Long, Double, Float : 按数字大小排序;
Character : 按字符的Unicode值的数字大小排序;
String : 按字符串中字符的Unicode值排序;
2).自定义排序: 客户端排序
创建比较器--->实现java.util.Comparator接口,重写compare(Object x, Object y)方法。
使用:
1,写一个比较器(类),实现Comparator接口,重写compare()方法。
2,创建该比较器的实例对象。
3,将比较器的对象 通过TreeSet的构造器交给TreeSet使用 : eg: new TreeSet(comparator);
3).另外写比较类,实现comparator接口,重写compare方法,需要把比较类的名字放进去
Set<String> s3 = new TreeSet<String>(com);
一般用匿名内部类写比较器,重写compare方法;
4).例: 1,创建Student类,name属性,age属性
2,写Test.java 写main方法, 在main方法中创建TreeSet集合。
3,TreeSet集合添加4个Student对象
4,输出,需要按照年纪大小排序, 大---->小
TreeSet<Student> set = new TreeSet<Student>(
new Comparator<Student>() {
@Override
public int compare(Student o1, Student o2) {
//o1为新加入的,o2为原来的
//返回负数,交换
//返回正数,放在后面
return o1.getAge()-o2.getAge();
}
}
);
set.add(new Student("lili",12));
set.add(new Student("zhangsan",37));
set.add(new Student("lala",32));
set.add(new Student("xiaoming",23));
set.add(new Student("xiaona",5));
Iterator<Student> iterator = set.iterator();
while(iterator.hasNext()) {
Student next = iterator.next();
System.out.println(next.getAge());
}
5)为什么TreeSet可以排序?
TreeSet是基于TreeMap实现的 ,利用了map保存的k-v键值对的key值不会重复的特点。
5.List:线性方式存储 可以重复 有序
1)ArrayList:长度可变的数组 底层是由数组实现
数组中查询和赋值比较快,因为可以直接通过数组下标访问指定位置。
2)LinkedList:链表结构 双向链表
链表中删除和增加比较快,因为可以直接通过修改链表的指针(Java中并无指针,这里可以简单理解为指针。其实是通过Node节点中的变量指定)进行元素的增删。
6.forEach 遍历---》加强for循环
for(String s:set){syso(s);}
7.Map
1)
1.1,)把键对象和值对象进行映射的集合,它的每一个元素都包含一对键对象和值对象。
1.2,)向Map集合中加入元素时,必须提供一对键对象和值对象. map.put(key,value);
1.3,)从Map集合中检索元素时,只要给出键对象,就会返回对应的值对象。value = map.get(key);
1.4,)Map集合中的键对象不允许重复,如果有多个相同的key那么上一次的值会被覆盖。
2.) HashMap : 判断key是否相同是通过 hashCode && equals方法来判断。
3)TreeMap : 实现了SortedMap接口,能对 键对象(key) 进行排序。
4)map的遍历:
4.1)keyset+迭代器
Set<Integer> set = map.keySet();
Iterator<Integer> itKey = set.iterator();
while(itKey.hasNext()){
Object key = itKey.next();
System.out.println(key + "---"+map.get(key));
}
4.2)keyset+加强for循环
Set<Integer> set = map.keySet();
for(Integer a: set) {
System.out.println(a+"----"+map.get(a));
}
4.3)map.entrySet()+迭代器循环
Iterator<Entry<Integer, String>> iterator = map.entrySet().iterator();
while(iterator.hasNext()){
Entry<Integer, String> next = iterator.next();
Integer key = next.getKey();
String value = next.getValue();
System.out.println(key+"===="+value);
}