Java的Iterator迭代器补充,增强for循环,泛型,List接口,set接口
Posted 孙崇武
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Java的Iterator迭代器补充,增强for循环,泛型,List接口,set接口相关的知识,希望对你有一定的参考价值。
1、Iterator迭代器:
(1)类型转换异常:ClassCastException;集合中存放的是多个对象时,在强转时会出现;
package com.oracle.demo01; import java.util.ArrayList; import java.util.Collection; import java.util.Iterator; public class demo01 { public static void main(String[] args) { method03(); }public static void method03(){ Collection col = new ArrayList(); col.add("123"); col.add(123); Iterator it = col.iterator(); while(it.hasNext()){ if(it.next() instanceof String){ //这里的两个it.next()不是一个 String s = (String)it.next(); System.out.println(s); } } } }
会出现以下异常:
(2)添加泛型避免异常;在编译时期出现编译失败;
与上面对比:
package com.oracle.demo01; import java.util.ArrayList; import java.util.Collection; import java.util.Iterator; public class demo01 { public static void main(String[] args) { Collection<String> col = new ArrayList<String>(); col.add("abc"); col.add("def"); Iterator<String> it = col.iterator(); while(it.hasNext()){ System.out.println(it.next()); } method03(); } public static void method03(){ Collection col = new ArrayList(); col.add("123"); col.add(123); Iterator it = col.iterator(); while(it.hasNext()){ if(it.next() instanceof String){ String s = (String)it.next(); System.out.println(s); } } } }
效果如下:
当添加元素时:The method add(String) in the type Collection<String> is not applicable for the arguments (int)
(3)并发修改异常:ConcurrentModificationException;对集合进行增删操作;
迭代器不知道集合中的变化,容易发生调用的不确定性,[ListIterator了解即可]
public class ListIteratorDemo { public static void main(String[] args) { List list = new ArrayList(); list.add("one"); list.add("two"); list.add("three"); list.add("five"); /*for(Iterator it = list.iterator(); it.hasNext();){ Object obj = it.next(); if(obj.equals("five")){ 在迭代过程中,如果使用了集合的方法进行增删改查操作,那么迭代器会抛出异常. 原因是,迭代器不知道集合中的变化,容易发生调用的不确定性. 解决办法: 在迭代时,不要使用集合的方法进行操作元素. 可以使用迭代器的子接口ListIterator<E>中的方法就可以. 里面有很多操作元素的方法.而且可以正向迭代,反向迭代. * //list.add("four"); // 异常 ConcurrentModificationException } System.out.println(obj); }*/ //用ListIterator重新解决问题 for(ListIterator it = list.listIterator(); it.hasNext();){ Object obj = it.next(); if("three".equals(obj)){ it.add("four"); //[one, two, three, four, five] // it.set("3"); //[one, two, 3, five] //对比输出结果 } } System.out.println(list); } }
2、增强for循环:
(1)for(元素的数据类型 变量:Collection集合or数组){ };
package com.oracle.demo01; import java.util.ArrayList; import java.util.Collection; public class demo03 { public static void main(String[] args) { Collection<demo02> col = new ArrayList<demo02>(); col.add(new demo02("熊大",12)); col.add(new demo02("熊二",13)); //普通for ArrayList<demo02> list = (ArrayList<demo02>)col; for(int i = 0;i < list.size();i++){ System.out.println(list.get(i)); } //增强for遍历集合 for(demo02 p:col){ System.out.println(p); } } }
效果都是一样的:
(2)无法进行1-100求和等操作;因为目标只能是数组和集合
(3)相当于一个迭代器:不要进行增删操作;
3、泛型:
(1)修饰符 class 类名<代表泛型的变量E> { }
举个例子:
package com.oracle.demo02; public class demo04 <E>{ public static void main(String[] args) { demo04<String> s = new demo04<String>(); } }
(2)将运行时期的ClassCastException,转移到了编译时期变成了编译失败。
避免了类型强转的麻烦;
(3)泛型和注释不进class文件;
4、List接口[有序、可重复]:
(1)并发修改异常解决办法:在迭代时,不要使用集合的方法操作元素;
package com.oracle.demo02; import java.util.ArrayList; import java.util.Iterator; import java.util.List; public class demo01 { public static void main(String[] args) { List<String> list = new ArrayList<String>(); list.add("abc"); list.add("def"); //Iterator 迭代器遍历 Iterator<String> it = list.iterator(); //找到“def”这个元素时,在“def”这个位置添加一个元素叫做ghi while(it.hasNext()){ if(it.next().equals("def")){ list.add("ghi"); } } } }
效果如下:
(2)List集合存储数据的结构:
堆栈:先进后出;压栈;栈的入口、出口都是栈的顶端位置;弹栈;
队列:先进先出;队列的入口、出口各占一侧;
数组:查找元素快;增删元素慢;
链表:多个节点之间,通过地址链接;查找元素慢;增删元素快;
(3)ArrayList集合数据存储的结构是数组结构:查找元素快;增删元素慢
LinkedList集合数据存储的结构是链表结构:查找元素慢;增删元素快;
(4)Vector集合[认识即可]:已被ArrayList替代;
5、set接口[无序、不重复]:
(1)HashSet集合:采用哈希表结构存储数据,保证元素唯一性的方式依赖于:hashCode()与equals()方法
在给哈希表中存放对象时,会调用对象的hashCode方法,算出对象在表中的存放位置,这里需要注意,
如果两个对象hashCode方法算出结果一样,这样现象称为哈希冲突,这时会调用对象的equals方法,
比较这两个对象是不是同一个对象,如果equals方法返回的是true,那么就不会把第二个对象存放在哈希表中,
如果返回的是false,就会把这个值存放在哈希表中;
(2)HashSet集合存储API类时:已经重写了hashCode方法和equals方法,如String类、Integer类等;
HashSet集合存储自定义类时:需要重写hashCode方法和equals方法,来确保HashSet集合中的对象唯一;
举个例子:
建立一个 demo02类:
package com.oracle.demo01; public class demo02 { private String name; private Integer age; public demo02() { super(); } public demo02(String name, Integer age) { super(); this.name = name; this.age = age; } public String toString() { return "demo01 [name=" + name + ", age=" + age + "]"; } public String getName() { return name; } public void setName(String name) { this.name = name; } public Integer getAge() { return age; } public void setAge(Integer age) { this.age = age; } public int hashCode() { final int prime = 31; int result = 1; result = prime * result + ((age == null) ? 0 : age.hashCode()); result = prime * result + ((name == null) ? 0 : name.hashCode()); return result; } public boolean equals(Object obj) { if (this == obj) return true; if (obj == null) return false; if (getClass() != obj.getClass()) return false; demo02 other = (demo02) obj; if (age == null) { if (other.age != null) return false; } else if (!age.equals(other.age)) return false; if (name == null) { if (other.name != null) return false; } else if (!name.equals(other.name)) return false; return true; } }
此时再进行存数据时:
package com.oracle.demo01; import java.util.HashSet; public class hash { public static void main(String[] args) { HashSet<demo02> set = new HashSet<demo02>(); set.add(new demo02("a",18)); set.add(new demo02("b",19)); set.add(new demo02("c",20)); set.add(new demo02("a",18)); for(demo02 p:set){ System.out.println(p); } } }
效果如下:
以上是关于Java的Iterator迭代器补充,增强for循环,泛型,List接口,set接口的主要内容,如果未能解决你的问题,请参考以下文章
java基础(18):集合Iterator迭代器增强for循环泛型