java list数据结构_java数据结构3--List

List

1.1 list接口的简介

64289d24ce9f8b8b6faeb35431c1cc6b.png

630b284f8ab9c817903d129be7ea6e15.png

03b8de837ee233ef0eaac32a086e8097.png

11bd02c066b11191c74865b86cc64d39.png

1.2 list实现子类

bd3bdf23e2ed68b3c4b11758e2f8f07e.png

ArrayList:

线程不安全,查询速度快,底层用的是数组,增删慢

LinkedList:

线程不安全,链表结构,增删速度快,查询慢

Vector:

线程安全,但速度慢,已被ArrayList替代

1.3 list的遍历方法

7ebe35d4b270aba8dd2cedf6eb60d16e.png

e660120f89f1b1448dbfee2b5cef8945.png

迭代器注意事项:

迭代器在Collcection接口中是通用的

迭代器的next方法返回值类型是Object,如果需要所以要记得类型转换。

12b7e4ce7a8adb1172994195e6327e78.png

1.4练习

1.使用ArrayList存储基本数据类型对象,并遍历2.使用ArrayList存储字符串对象,并遍历

8f900a89c6347c561fdf2122f13be562.png

961ddebeb323a10fe0623af514929fc1.png

importjava.util.ArrayList;/** 使用ArrayList存储基本数据类型对象,并遍历*/

public classDemo1 {public static voidmain(String[] args) {//Colletion//List

ArrayList list = newArrayList();

list.add(10);//此处发生的是自动装箱int --> Integer 1.5

list.add(true);//Boolean

list.add(3.14);//Double

list.add('a');//Character

/**

*

* list.add(Integer.valueOf(10));

list.add(Boolean.valueOf(true));

list.add(Double.valueOf(3.1400000000000001D));

list.add(Character.valueOf('a'));*/

for(Object object : list) {

System.out.println(object);

}

}

}

练习1

练习2:

c2a78575703928e41f8a1fe4eb7c4c6f.png

3.使用ArrayList存储自定义类型对象,并遍历4.使用ArrayList实现字符串的去重

8f900a89c6347c561fdf2122f13be562.png

961ddebeb323a10fe0623af514929fc1.png

importjava.util.ArrayList;/** 使用ArrayList存储自定义类型对象,并遍历

*

*

* 快速生成Getters Setters :

* alt + shift + s : --> Generate getters and setters

-->空参构造方法

-->带参构造方法*/

classStudent {privateString name;private intage;publicString getName() {returnname;

}public voidsetName(String name) {this.name =name;

}public intgetAge() {returnage;

}public void setAge(intage) {this.age =age;

}publicStudent() {super();//TODO Auto-generated constructor stub

}public Student(String name, intage) {super();this.name =name;this.age =age;

}

@OverridepublicString toString() {return "Student [name=" + name + ", age=" + age + "]";

}

}public classDemo3 {public static voidmain(String[] args) {

ArrayList list= newArrayList();//创建自定义对象

Person s1 = new Person("张三", 15);

Person s2= new Person("李四", 25);

Person s3= new Person("王五", 20);//添加到集合

list.add(s1);

list.add(s2);

list.add(s3);//添加匿名对象

list.add(new Person("tom", 16));for(Object obj : list) {

Person s= (Person) obj;//元素类型确切是Student才能强转成功//System.out.println(s.getName() + "--" + s.getAge());//System.out.println(s.toString());

System.out.println(s);//间接调用toString方法

}

}

}

练习3

8f900a89c6347c561fdf2122f13be562.png

961ddebeb323a10fe0623af514929fc1.png

importjava.util.ArrayList;/** 使用ArrayList实现字符串的去重

*

* 思路:

* 创建一个新的集合.

* 把原集合中的元素取出,在新集合中进行判断.如果包含,就不添加,如果不包含,就添加.

* 遍历完,新集合中就是去重之后的结果.

*

* 不创建新集合实现去重:

* 思路:从前往后比较,注意删除元素后,后面的元素会向前移位

*

**/

public classDemo4 {public static voidmain(String[] args) {/*ArrayList list = new ArrayList();

list.add("abc");

list.add("abc");

list.add("abc2");

list.add("abc2");

list.add("world");

//创建一个新集合

ArrayList list2 = new ArrayList();

for (Object obj : list) {

//contains

if(!list2.contains(obj)){

list2.add(obj);

}

}

//打印新集合内容

System.out.println(list2);//调用toString方法*/ArrayList list= newArrayList();

list.add("abc");

list.add("abc");

list.add("abc");

list.add("abc2");

list.add("abc2");

list.add("abc2");

list.add("abc2");

list.add("abc3");

list.add("abc3");

list.add("abc3");

list.add("abc3");

list.add("abc3");//从前往后比较,注意删除元素后,后面的元素会向前移位

/*for(int i = 0;i

for(int j = i + 1;j

if(list.get(i).equals(list.get(j))){

list.remove(j);

j--;

}

}

}*/

//2.从后往前比较

for(int i = 0;ii;j--){if(list.get(i).equals(list.get(j))){

list.remove(j);

}

}

}

System.out.println(list);

}

}

练习4

8f900a89c6347c561fdf2122f13be562.png

961ddebeb323a10fe0623af514929fc1.png

importjava.util.ArrayList;/**重写equals方法原则

* 1.先进行非空判断

* 2.转换成同类型

* 3.对所有的成员变量进行比较,所有的成员变量都相同的情况下才是相同的对象

*

**/

classPerson {privateString name;private intage;publicString getName() {returnname;

}public voidsetName(String name) {this.name =name;

}public intgetAge() {returnage;

}public void setAge(intage) {this.age =age;

}publicPerson() {super();

}public Person(String name, intage) {super();this.name =name;this.age =age;

}

@OverridepublicString toString() {return "Person [name=" + name + ", age=" + age + "]";

}

@Overridepublic booleanequals(Object obj) {if (this ==obj)return true;if (obj == null)return false;if (getClass() !=obj.getClass())return false;

Person other=(Person) obj;if (age !=other.age)return false;if (name == null) {if (other.name != null)return false;

}else if (!name.equals(other.name))return false;return true;

}/** 重写equals方法,告诉虚拟机什么情况下两个对象才是相同的对象

* 步骤:非空判断 --> 类型转换 --> 成员变量比较*/

/*@Override

public boolean equals(Object obj) {

// return true;

//所有的成员变量都相同的情况下,两个对象才是相等的.

if(obj == null){

return false;

}

//把传入的参数进行类型转换,同类才能比

Person p = (Person)obj;

int age2 = p.getAge();

String name2 = p.getName();

if(age2 == age && name.equals(name2)){

return true;

}

//出现任何一个成员变量不同,都不能称为相同的对象.

return false;

}*/}public classDemo5 {public static voidmain(String[] args) {

ArrayList list= newArrayList();//创建自定义对象

Person p1 = new Person("tom",15);

Person p2= new Person("toms",16);

list.add(p1);

list.add(p2);//创建新集合

ArrayList list2 = newArrayList();for(Object obj : list) {if(!list2.contains(obj)){//底层调用的是equals方法.根据返回值判断是否能添加成功

list2.add(obj);

}

}for(Object object : list2) {

Person p=(Person)object;

System.out.println(p.getName()+"--"+p.getAge());

}

}

}

练习3

note:技巧

0aa251142b820bf0c116b738c3de2166.png

1.5 contains方法

思路:创建新集合,从原集合里拿出元素放入新集合,放入的同时做判断

使用的是contains方法

通过查看contains方法的源码,实际上调用的是要添加元素的equals方法

即:如果要添加元素对已经存在的元素调用equals方法,返回true表明已经存在,返回false表明不存在.

默认equals是继承自Object类的,只是简单的比较地址

自定义类要重写equals方法,告知虚拟机到底什么情况下对象才是”相等”的。

2bb59cfde59f3e72e9e35603e3890aa2.png

b09a205ef133a6448d4c305ee5526323.png

8f900a89c6347c561fdf2122f13be562.png

961ddebeb323a10fe0623af514929fc1.png

importjava.util.ArrayList;/**重写equals方法原则

* 1.先进行非空判断

* 2.转换成同类型

* 3.对所有的成员变量进行比较,所有的成员变量都相同的情况下才是相同的对象

*

**/

classPerson {privateString name;private intage;publicString getName() {returnname;

}public voidsetName(String name) {this.name =name;

}public intgetAge() {returnage;

}public void setAge(intage) {this.age =age;

}publicPerson() {super();

}public Person(String name, intage) {super();this.name =name;this.age =age;

}

@OverridepublicString toString() {return "Person [name=" + name + ", age=" + age + "]";

}

@Overridepublic booleanequals(Object obj) {if (this ==obj)return true;if (obj == null)return false;if (getClass() !=obj.getClass())return false;

Person other=(Person) obj;if (age !=other.age)return false;if (name == null) {if (other.name != null)return false;

}else if (!name.equals(other.name))return false;return true;

}/** 重写equals方法,告诉虚拟机什么情况下两个对象才是相同的对象

* 步骤:非空判断 --> 类型转换 --> 成员变量比较*/

/*@Override

public boolean equals(Object obj) {

// return true;

//所有的成员变量都相同的情况下,两个对象才是相等的.

if(obj == null){

return false;

}

//把传入的参数进行类型转换,同类才能比

Person p = (Person)obj;

int age2 = p.getAge();

String name2 = p.getName();

if(age2 == age && name.equals(name2)){

return true;

}

//出现任何一个成员变量不同,都不能称为相同的对象.

return false;

}*/}public classDemo5 {public static voidmain(String[] args) {

ArrayList list= newArrayList();//创建自定义对象

Person p1 = new Person("tom",15);

Person p2= new Person("toms",16);

list.add(p1);

list.add(p2);//创建新集合

ArrayList list2 = newArrayList();for(Object obj : list) {if(!list2.contains(obj)){//底层调用的是equals方法.根据返回值判断是否能添加成功

list2.add(obj);

}

}for(Object object : list2) {

Person p=(Person)object;

System.out.println(p.getName()+"--"+p.getAge());

}

}

}

练习3

1.6 并发修改异常

在使用迭代器和增强for循环遍历ArrayList的时候,使用集合本身的方法修改了集合,将导致并发修改异常:ConcurrentModificationException (两个不要交叉使用)

foreach本质上:是使用了迭代器

1.使用迭代器遍历,使用迭代器删除(修改)元素

2.使用集合本身遍历且非foreach,使用集合本身方法删除(修改)元素

cf550cbcab14d91617197a5814a11ecc.png

eedcfa4c076682caae0fc5212cd4e3d8.png

如何添加元素:

查看Iterator接口的方法,没有添加元素的方法

但是它的子接口ListIterator有添加元素的方法

c455a442033e9d11de08174142ae206b.png

6345635b31facf2514670445ada1cbaf.png

1.7 Vector类

Vector类是1.0就已经有的,在1.2被整合到集合框架中

其中的大部分方法都和ArrayList相同,但它是线程安全的,所以效率要低。

2b4bbb19bd8043cb31aab8e7129553db.png

importjava.util.Enumeration;importjava.util.Vector;/**

* jdk升级的原因:

* 1.提供新方法.

* 2.简化书写.*/

public classVectorDemo {public static voidmain(String[] args) {

Vector v= new Vector<>();

v.addElement("hello");

v.addElement("world");

System.out.println(v.size());

v.removeElement("hello");

System.out.println(v.size());

Enumeration en=v.elements();while(en.hasMoreElements()){

Object obj=en.nextElement();

System.out.println(obj);

}

}

}

1.8LinkedList类

LinkedList 类底层使用的是链表结构保存数据

LinkedList底层使用的是链表,但是自己维护了一个索引,

所以也提供了get(int index)的方法来通过索引获取元素

但此方法的效率很低,一般不使用。

绝大多数方法和ArrayList相同,只不过多了一些对首尾元素操作的方法

addFirst()

addLast()

remove()

3a91b645b76cea038a358224d610fd61.png

a681ae0566b2c544d3bd19784bf2ee42.png

练习:

使用LinkedList类模拟栈结构的集合.

注意是模拟栈结构,不是直接使用LinkedList,即:有一个集合,其中的元素是先进后出.

8f900a89c6347c561fdf2122f13be562.png

961ddebeb323a10fe0623af514929fc1.png

/** 练习:

使用LinkedList类模拟栈结构的集合.(FILO,LIFO)

注意是模拟栈结构,不是直接使用LinkedList,即:有一个集合,其中的元素是先进后出.

自己设计一个类:

最基本的方法:存, 取.

在此基础之上体现栈的特点:FILO

public class MyStack{

//成员位置包含一个LinkedList

LinkedList list = new LinkedList();

//add:真正操作的是list

//get:真正操作的是list

}*/

importjava.util.LinkedList;classMyStack{//在成员位置保持一个LinkedList的引用

LinkedList list = newLinkedList();//add

public voidadd(Object obj){

list.addFirst(obj);

}//get

publicObject get(){returnlist.pop();

}//提供判断是否含有元素方法

public booleanisEmpty(){returnlist.isEmpty();

}

}public classLinkedListDemo2 {public static voidmain(String[] args) {

MyStack ms= newMyStack();

ms.add("hello");

ms.add("world");

ms.add("java");

ms.add("hadoop");

ms.add("mysql");//

//System.out.println(ms.get());//System.out.println(ms.get());//System.out.println(ms.get());//System.out.println(ms.get());//System.out.println(ms.get());//System.out.println(ms.get());

while(!ms.isEmpty()){

System.out.println(ms.get());

}

}

}

模拟栈结构

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值