1.List接口介绍
- List是有序的 Collection(也称为序列)。此接口的用户可以对列表中每个元素的
插入位置进行精确地控制。用户可以根据元素的整数索引(在列表中的位置)访
问元素,并搜索列表中的元素。与 set 不同,列表通常允许重复的元素。
- List接口的特点:
1) 它是一个元素存取有序的集合。例如,存元素的顺序是11、22、33,那么集
合中元素的存储就是按照11、22、33的顺序完成的。
2)它是一个带有索引的集合,通过索引就可以精确的操作集合中的元素(与数组
的索引是一个道理)。
3)集合中可以有重复的元素,通过元素的equals方法,来比较是否为重复的元素。
- List接口的常用子类有:
1 ) ArrayList集合
2 ) LinkedList集合
3 ) Vector集合
1.1常用方法
Modifier and Type | Method and Description |
---|---|
boolean |
add(E e) 将指定的元素追加到此列表的末尾。 |
void |
add(int index, E element) 在此列表中的指定位置插入指定的元素。 |
void |
clear() 从列表中删除所有元素。 |
boolean |
contains(Object o) 如果此列表包含指定的元素,则返回 true 。 |
E |
get(int index) 返回此列表中指定位置的元素。 |
boolean |
isEmpty() 如果此列表不包含元素,则返回 true 。 |
Iterator<E> |
iterator() 以正确的顺序返回该列表中的元素的迭代器。 |
E |
remove(int index) 删除该列表中指定位置的元素。 |
boolean |
remove(Object o) 从列表中删除指定元素的第一个出现(如果存在)。 |
boolean |
removeAll(Collection<?> c) 从此列表中删除指定集合中包含的所有元素。 |
E |
set(int index, E element) 用指定的元素替换此列表中指定位置的元素。 |
int |
size() 返回此列表中的元素数。 |
2.ArraysList
2.1介绍
ArrayList集合数据存储的结构是数组结构。元素增删慢,查找快,由于日常开
发中使用最多的功能为查询数据、遍历数据,所以ArrayList是最常用的集合。
许多程序员开发时非常随意地使用ArrayList完成任何需求,并不严谨,这种用
法是不提倡的。
2.2代码示例
package Collection_list_map.list;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
class Teacher{
private String name;//老师姓名
private String no;//老师工号
public Teacher(String name, String no) {
this.name = name;
this.no = no;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getNo() {
return no;
}
public void setNo(String no) {
this.no = no;
}
@Override
public String toString() {
return "Teacher{" +
"name='" + name + '\'' +
", no='" + no + '\'' +
'}';
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Teacher teacher = (Teacher) o;
return Objects.equals(this.name, teacher.name) &&
Objects.equals(this.no, teacher.no);
}
}
public class ArraysList {
public static void main(String[] args) {
Teacher t1 = new Teacher("wcq","35");
Teacher t2 = new Teacher("kql","36");
Teacher t3 = new Teacher("hej","34");
Teacher t4 = new Teacher("wcq","35");
List<Teacher> list = new ArrayList<Teacher>();
list.add(t1);
list.add(t2);
list.add(t3);
System.out.println("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~");
for (int i = 0; i < list.size(); i++) {
System.out.println(list.get(i).toString());
System.out.println(list.get(i));
}
System.out.println("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~");
System.out.println(list.get(1).toString());
System.out.println("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~");
list.remove(2);
for (int i = 0; i < list.size(); i++) {
System.out.println(list.get(i).toString());
}
System.out.println("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~");
System.out.println(list.isEmpty());
System.out.println("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~");
System.out.println(list.contains(t1));
System.out.println("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~");
System.out.println(list.contains(t4));
System.out.println("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~");
list.clear();
for (int i = 0; i < list.size(); i++) {
System.out.println(list.get(i).toString());
}
System.out.println("说明没有数据");
}
}
运行结果:
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Teacher{name='wcq', no='35'}
Teacher{name='wcq', no='35'}
Teacher{name='kql', no='36'}
Teacher{name='kql', no='36'}
Teacher{name='hej', no='34'}
Teacher{name='hej', no='34'}
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Teacher{name='kql', no='36'}
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Teacher{name='wcq', no='35'}
Teacher{name='kql', no='36'}
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
false
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
true
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
true
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
说明没有数据
2.3 底层结构
- ArrayList底层的数据结构使用的是数组。
这种数据结构的特点是:
1)查找元素快:通过索引,可以快速访问指定位置的元素
-
增删元素慢:
2.1)指定索引位置增加元素:需要创建一个新数组,将指定新元素存储在指定索引位置,再把原数组元素根据索引,复制到新数组对应索引的位置。
2.2) 指定索引位置删除元素:需要创建一个新数组,把原数组元素根据索引,复制到新数组对应索引的位置,原数组中指定索引位置元素不复制到新数组中。
2.4contains方法检查元素是否重复
ArrayList的contains方法判断元素是否存在,判断的原理如下:
ArrayList的contains方法被调用时,用传入元素的equals方法依次与集合中的旧元素进行比较,根据返回的布尔值判断是否有重复元素。此时,当ArrayList存放自定义类型时,由于自定义类型在未重写equals方法前,判断是否重复的依据是地址值,所以如果想根据内容判断是否为重复元素,需要重写元素的equals方法。
- Teacher类未重写equals方法前,判断集合中是否包含指定的老师
public static void main(String[] args) {
//1:创建两个工号和姓名相同老师对象
Teacher t1 = new Teacher("02", "刘邦");
Teacher t2 = new Teacher("02", "刘邦");
//2:创建老师集合
List<Teacher> list =new ArrayList<Teacher>();
//3:向集合中添加t1老师
list.add(t1);
//4:判断list集合中是否有t2老师
System.out.println(list.contains(t2));//结果是false
}
最后一行代码 t2调用equals方法与list集合中的每一个对象比较,默认比较内存地址编号。
- 在老师类中重新equals方法
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Teacher teacher = (Teacher) o;
return Objects.equals(this.name, teacher.name) &&
Objects.equals(this.no, teacher.no);
}
Teacher类重写equals方法后,再次运行程序
public static void main(String[] args) {
//1:创建两个工号和姓名相同老师对象
Teacher t1 = new Teacher("02", "刘邦");
Teacher t2 = new Teacher("02", "刘邦");
//2:创建老师集合
List<Teacher> list =new ArrayList<Teacher>();
//3:向集合中添加t1老师
list.add(t1);
//4:判断list集合中是否有t2老师
System.out.println(list.contains(t2));//结果是true
}
最后一行 t2调用equals方法与list集合中的每一个对象比较,调用的是重写后的equals方法。
3.Vector
Vector集合数据存储的结构是数组结构,为JDK中最早提供的集合。Vector中提
供了一个独特的取出方式,就是枚举Enumeration,它其实就是早期的迭代器。
此接口Enumeration的功能与 Iterator 接口的功能是类似的。Vector集合已被
ArrayList替代。枚举Enumeration已被迭代器Iterator替代。
Vector与ArrayList不同的是Vector类是线程安全的,ArrayList是非线程安全的。
Vector的用法与ArrayList相同:
/**
* 使用Vector集合操作Teacher对象
*/
class Teacher {
private String name;//老师姓名
private String no;//老师工号
public Teacher(String name, String no) {
this.name = name;
this.no = no;
}
@Override
public String toString() {
return "Teacher{" +
"name='" + name + '\'' +
", no='" + no + '\'' +
'}';
}
}
public class Demo {
public static void main(String[] args) {
//1:创建三个老师对象
Teacher t1 = new Teacher("01", "朱元璋");
Teacher t2 = new Teacher("02", "刘邦");
Teacher t3 = new Teacher("03", "李自成");
//2:创建老师集合
List<Teacher> list = new Vector<>();
//3:向集合中添加老师
list.add(t1);
list.add(t2);
list.add(t3);
//4:迭代(遍历)老师
System.out.println("======================");
show(list);
//5:从集合中获取第一个老师
System.out.println("======================");
Teacher t = list.get(0);
System.out.println(t);
//6:删除第一个老师
list.remove(0);
System.out.println("======================");
show(list);
//7:显示集合中老师的人数
System.out.println(list.size());
//8:集合中有老师吗
System.out.println(list.isEmpty());
//9:查找刘邦老师
System.out.println(list.contains(t2));
//10:逐一删除集合中的数据
int last = list.size();
for (int i = 0; i < last; i++) {
list.remove(0);
}
//11:批量删除
list.clear();
System.out.println("======================");
show(list);
}
private static void show(List<Teacher> list) {
Iterator<Teacher> iterator = list.iterator();
while (iterator.hasNext()) {
System.out.println(iterator.next());
}
}
}
4.LinkedList类
4.1介绍
LinkedList集合数据存储的结构是链表结构。方便元素添加、删除的集合。实际开发中对一个集合元素的添加与删除经常涉及到首尾操作,而LinkedList提供了大量首尾操作的方法。
LinkedList类是List的子类,List中的方法LinkedList都是可以使用。在开发时,LinkedList集合也可以作为栈,队列的结构使用,LinkedList类为栈和队列操作提供了相应的方法。
4.2常用方法
Modifier and Type | Method and Description |
---|---|
boolean |
add(E e) 将指定的元素追加到此列表的末尾。 |
void |
add(int index, E element) 在此列表中的指定位置插入指定的元素。 |
void |
addFirst(E e) 在该列表开头插入指定的元素。 |
void |
addLast(E e) 将指定的元素追加到此列表的末尾。 |
void |
clear() 从列表中删除所有元素。 |
boolean |
contains(Object o) 如果此列表包含指定的元素,则返回 true 。 |
E |
get(int index) 返回此列表中指定位置的元素。 |
E |
getFirst() 返回此列表中的第一个元素。 |
E |
getLast() 返回此列表中的最后一个元素。 |
E |
pop() 从此列表表示的堆栈中弹出一个元素。 |
void |
push(E e) 将元素推送到由此列表表示的堆栈上。 |
E |
remove() 检索并删除此列表的头(第一个元素)。 |
E |
remove(int index) 删除该列表中指定位置的元素。 |
boolean |
remove(Object o) 从列表中删除指定元素的第一个出现(如果存在)。 |
E |
removeFirst() 从此列表中删除并返回第一个元素。 |
E |
removeLast() 从此列表中删除并返回最后一个元素。 |
E |
set(int index, E element) 用指定的元素替换此列表中指定位置的元素。 |
int |
size() 返回此列表中的元素数。 |
Object[] |
toArray() 以正确的顺序(从第一个到最后一个元素)返回一个包含此列表中所有元素的数组。 |
<T> T[] |
toArray(T[] a) 以正确的顺序返回一个包含此列表中所有元素的数组(从第一个到最后一个元素); |
4.3代码演示
List中的方法LinkedList都是可以使用,这里不再给出例子,请参考ArrayList类的代码演示。
在这里给出LinkedList的特有操作方法。
public static void main(String[] args) {
//1:创建两个工号和姓名相同老师对象
Teacher t1 = new Teacher("01", "朱元璋");
Teacher t2 = new Teacher("02", "刘邦");
Teacher t3 = new Teacher("03", "李自成");
//2:创建老师集合
LinkedList<Teacher> list =new LinkedList<>();
//添加元素
list.addFirst(t1);
list.addFirst(t2);
list.addLast(t3);
//获取元素
System.out.println(list.getFirst());
System.out.println(list.getLast());
//删除元素
System.out.println(list.removeFirst());
System.out.println(list.removeLast());
while(!list.isEmpty()){ //判断集合是否为空
System.out.println(list.pop()); //弹出集合中的栈顶元素,栈顶元素从集合中被移除
}
}
4.4底层数据结构
LinkedList底层的数据结构使用的是链表。
这种数据结构的特点是:
- 查找元素慢:想查找某个元素,需要通过连接的节点,依次向后查找指定元素
- 增删元素快:增加元素,只需要修改连接下个元素的地址即可,所有元素无需移动位置
-
删除元素快:只需要修改连接下个元素的地址即可,所有元素无需移动位置