重点
1.泛型迭代器
Iterator<String> iterator;
Iterator<Student> iterator;
public static void main(String[] args) {
// TODO Auto-generated method stub
//泛型集合
//1.声明一个泛型集合
List\<String> list = new ArrayList\<String>();
list.add("abc");
list.add("efg");
//list.add(1);
//2.遍历1
/*for(int i=0;i\<list.size();i++){
//泛型可以避免强制类型转换
String str = list.get(i);
System.out.println(str);
}*/
//3.遍历2
List list2 = new ArrayList();
//泛型迭代器
Iterator\<String> iterator = list.iterator();
while(iterator.hasNext()){
//取元素
String str = iterator.next();//方法返回值是String
System.out.println(str);
}
}
2.泛型注意事项
// 1.默认声明一个泛型集合,前后类型要一至
List<Student> list1 = new ArrayList<Student>();
// 2.这样声明前后类型不一至是不可以的
//不可以前面写父类,后面写子类
//List<Object> list2 = new ArrayList<Student>();
// 3.集合泛型的声明,可以只声明前面的泛型,jdk1.7的新特性:菱形泛型,开发时建议还是写成前后一至
//1.6 1.5的jdk不能写菱形泛型
List<Student> list3 = new ArrayList<>();
// 4.集合声明的泛型,代表此类或者子类都可以成为集合的元素,eg: Person -> Student
List<Person> list4 = new ArrayList<Person>();
// 5.声明的泛型类型一定是引用数据类型(类)
//泛型是基本数据类型
//List<int> list6 = new ArrayList<int>();
List<Float> list6 = new ArrayList\();
3.泛型的由来
- 解决类型转换异常
4.声明泛型类和泛型方法
掌握:
如何声明一个泛型类和方法
1.声明一个泛型类
class Tool<T>
声明泛型方法格式: public 返回类型(T) 方法名(泛型类型T 变量名)
2.声明一个泛型方法(无返回值,有泛型参数)
public void print(T t)
3.声明一个泛型方法(有返回值,无参数)
public T get(int index)
4.声明一个泛型属性
private T o;
public T getO() {
return o;
}
public void setO(T o) {
this.o = o;
}
5.泛型高级之通配符
// 1.泛型通配符\<?> 一般在声明变量类型时使用
// 任意类型,如果没有明确,那么就是Object以及任意的Java类了
//打印集合对象
public static void print(List<?> list){
System.out.println(list);
}
// 2.? extends E 【E是父类,?子类】
// 向下限定,E及其子类
/**
* addAll(Collection<? extends Person> c)
* 添加的集合可以是 Person类型【List\ list4】,或者是Person的子类【List<Student> list6】
*/
//List<Person> list5 = new ArrayList<Person>();
/**
* addAll(Collection\<? extends Student> c)
* 添加的集合可以是 Student类型【List\<Student> list6】,或者是Student的子类【List\<Person> list4】
*/
List\<Student> list5 = new ArrayList\<Student>();
// 3.? super E 【?是父类,E子类】- 暂时先不掌握
// 向上限定,E及其父类
public static void main(String[] args) {
// TODO Auto-generated method stub
//泛型高级之通配符
// 1.泛型通配符\<?> 一般在声明变量类型时使用
// 任意类型,如果没有明确,那么就是Object以及任意的Java类了
List\<Object> list = new ArrayList\<Object>();
//List\<?> list = new ArrayList\<?>();//声明时右边不能用?号
list.add(1);
list.add("abc");
list.add(9.89);
list.add(new Student("小李", 12));
List\<String> list2 = new ArrayList\<String>();
list2.add("a");
list2.add("b");
print(list2);
List\<Student> list3 = new ArrayList\<Student>();
list3.add(new Student());
list3.add(new Student());
print(list3);
// 2.? extends E 【E是父类,?子类】
// 向下限定,E及其子类
List\<Person> list4 = new ArrayList\<Person>();
list4.add(new Person());
list4.add(new Person());
list4.add(new Person());
/**
* addAll(Collection\<? extends Person> c)
* 添加的集合可以是 Person类型【List\<Person> list4】,或者是Person的子类【List\<Student> list6】
*/
//List\<Person> list5 = new ArrayList\<Person>();
/**
* addAll(Collection\<? extends Student> c)
* 添加的集合可以是 Student类型【List\<Student> list6】,或者是Student的子类【List\<Person> list4】
*/
List\<Student> list5 = new ArrayList\<Student>();
//list5.add(new Person());
//list5.addAll(list4);//把list4的3个元素添加到list5中
System.out.println(list5);
List\<Student> list6 = new ArrayList\<Student>();
list6.add(new Student());
list6.add(new Student());
list5.addAll(list6);//把list6的2个元素添加到list5中
System.out.println(list5);
// 3.? super E 【?是父类,E子类】- 暂时先不掌握
// 向上限定,E及其父类
}
//打印集合对象
public static void print(List\<?> list){
System.out.println(list);
}
6.增强for循环
简化数组和集合遍历
格式:
for(元素数据类型 变量 : 数组或者Collection集合) {
使用变量即可,该变量就是元素
}
int[] arr1 = {120,110,119};
for(int num : arr1){
System.out.println(num);
}
//2.集合
List\<String> list = new ArrayList\<String>();
list.add("小子");
list.add("孙子");
list.add("老子");
int i = 0;
for(String str : list){
i++;
System.out.println("第" + i + "个元素:" + str);
}
7.Dao
- 数据访问层
public class Demo01 {
public static void main(String[] args) {
//创建泛型集合
List\<String> list = new ArrayList\<String>();
//泛型接口
/* 泛型接口概述
把泛型定义在接口
定义格式
public interface 接口名\<泛型类型>*/
//使用Dao
StudentDao stuDao = new StudentDao();
List\<Student> stuList = stuDao.findList();
System.out.println("stuList:" + stuList);
EmployeeDao empDao = new EmployeeDao();
List\<Employee> empList = empDao.findList();
System.out.println("empList:" + empList);
}
}
//获取学生信息
class StudentDao{
/**
* 从数据库获取学生信息
* @return
*/
public List\<Student> findList(){
List\<Student> list = new ArrayList\<Student>();
list.add(new Student("小王", 18));
list.add(new Student("小李", 28));
return list;
}
}
//获取员工信息
class EmployeeDao{
/**
* 从数据库获取员工信息
* @return
*/
public List\<Employee> findList(){
List\<Employee> list = new ArrayList\<Employee>();
list.add(new Employee("小郭", 38));
list.add(new Employee("小红", 28));
return list;
}
}
8.泛型Dao接口
public class Demo01 {
public static void main(String[] args) {
//创建泛型集合
List\<String> list = new ArrayList\<String>();
//泛型接口
/* 泛型接口概述
把泛型定义在接口
定义格式
public interface 接口名\<泛型类型>*/
//使用Dao
DaoInterface\<Student> stuDao = new StudentDao();
System.out.println("stuList:" + stuDao.findList());
DaoInterface\<Employee> empDao = new EmployeeDao();
System.out.println("empList:" + empDao.findList());
}
}
//发现Dao操作数据库的方法一样
/**
* 数据访问层的接口
* 1.接口一般都定义方法
*
*/
interface DaoInterface\<T>{
public List\<T> findList();//查找表的所有信息
public T findByName(String name);//根据名字查询信息
public void update(T t);//修改信息
}
//泛型接口的实现类
class StudentDao implements DaoInterface\<Student>{
@Override
public List\<Student> findList() {
List\<Student> list = new ArrayList\<Student>();
list.add(new Student("小王", 18));
list.add(new Student("小李", 28));
return list;
}
@Override
public Student findByName(String name) {
// TODO Auto-generated method stub
return null;
}
@Override
public void update(Student t) {
// TODO Auto-generated method stub
}
}
class EmployeeDao implements DaoInterface\<Employee>{
@Override
public List\<Employee> findList() {
List\<Employee> list = new ArrayList\<Employee>();
list.add(new Employee("小郭", 38));
list.add(new Employee("小红", 28));
return list;
}
@Override
public Employee findByName(String name) {
// TODO Auto-generated method stub
return null;
}
@Override
public void update(Employee t) {
// TODO Auto-generated method stub
}
}
9.三种迭代能否删除元素
- 普通for循环,可以删除,但是索引要(–减减 )
- 迭代器,可以删除,但是必须使用迭代器自身的remove方法,否则会出现并发修改异常
- 增强for循环不能删除
public static void main(String[] args) {
//三种迭代的能否删除
/***
* 迭代 = 遍历
*
*
*/
// 1.普通for循环,可以删除,但是索引要(--减减 )
//test1();
// 2.迭代器,可以删除,但是必须使用迭代器自身的remove方法,否则会出现并发修改异常
//test2();
// 3.增强for循环不能删除
test3();
}
private static void test3() {
//增强for循环不能删除
//增强for循环,内部的实现机制就迭代器
List\<String> list = new ArrayList\<String>();
list.add("java");
list.add("mysql");
list.add("h5");
list.add("h5");
list.add("css");
//迭代
for(String str : list){
if(str.equals("h5"));
list.remove(str);
}
}
private static void test2() {
//迭代器,可以删除,但是必须使用迭代器自身的remove方法,否则会出现并发修改异常
List\<String> list = new ArrayList\<String>();
list.add("java");
list.add("mysql");
list.add("h5");
list.add("h5");
list.add("css");
//迭代
Iterator\<String> iterator = list.iterator();
while(iterator.hasNext()){
String str = iterator.next();
if(str.equals("h5")){
//list.remove("h5");
iterator.remove();//移除当前遍历的元素
}
}
System.out.println("lsit:" + list);
}
private static void test1() {
//普通for循环,可以删除,但是索引要(--减减 )
List\<String> list = new ArrayList\<String>();
list.add("java");
list.add("mysql");
list.add("h5");
list.add("h5");
list.add("css");
//遍历
//int size = list.size();//把size提取到外面会有数组越界的问题
for(int i=0;i \< list.size(); i++){
System.out.println(i);
//取出元素
String str = list.get(i);
if(str.equals("h5")){
list.remove("h5");
i--;
}
}
System.out.println("list:" + list);
}
10.静态导入[很少用]
静态导入是只导入类的静态方法
import static 包名+类名+方法名;
11.可变参数
可变参数,就是调用方法的时候,可以传n个参数
test1(int … nums);//传n个数字
test2(Object … objs);//传n个任意对象
注意:如果方法有多个参数名,可变参数名必须要放在最后
12.Arrays.asList方法:把数组转成集合
List\<String> list1 = Arrays.asList("Gosling","Lucy","Lily");
System.out.println(list1);
List\<Student> list2 = Arrays.asList(new Student(),new Student(),new Student());
System.out.println(list2);
练习题
1.Collection的toArray方法:把集合的元素 添加到 指定数组中
public class Demo01 {
public static void main(String[] args) {
// TODO Auto-generated method stub
//Collection中toArray(T[] a)泛型版的集合转数组
Collection\<String> col = new ArrayList\<String>();
col.add("Gosling");
col.add("gyf");
//声明一个字符串数组
String[] strs = new String[2];
for(String str : strs){
System.out.println(str);
}
System.out.println("===================");
//把集合里的元素 存在 指定的数组中
col.toArray(strs);
for(String str : strs){
System.out.println(str);
}
/*Collection\<Student> col2 = new ArrayList\<Student>();
Student[] stus = new Student[2];
col2.toArray(stus);*/
}
}
2.集合嵌套之List嵌套List
案例需求
1.一个班的n学生是一个集合
2.一个学校n班也是一个集合
3.如何将这些数据用一个集合来表示
public class Demo01 {
public static void main(String[] args) {
//案例演示: 集合嵌套之List嵌套List
/* 案例需求
1.一个班的n学生是一个集合
2.一个学校n班也是一个集合
3.如何将这些数据用一个集合来表示
学校里有n个班,每个班有n个学生
*/
//1、用集合来表示两个班级
List\<Student> java1 = new ArrayList\<Student>();
java1.add(new Student("小刘", 18));
java1.add(new Student("小张", 18));
java1.add(new Student("小关", 18));
List\<Student> java2 = new ArrayList\<Student>();
java2.add(new Student("李某某", 18));
java2.add(new Student("黄某某", 18));
java2.add(new Student("李某某", 18));
//2.用集合来表示学校school
List\<List\<Student>> school = new ArrayList\<List\<Student>>();
school.add(java1);
school.add(java2);
//3.遍历
//3.1遍历班级
for(List\<Student> stus : school){
System.out.println("班级...");
//3.2 遍历学生
for(Student stu : stus){
System.out.println(stu);
}
}
}
}
总结
通过今天的学习,对泛型的用处有了更多的了解,可以用在迭代器,集合,属性,方法,类,接口等;泛型可以很好的解决类型转换异常。增强for循环内部实现实质是迭代器,在对数组以及集合遍历上很方便,但需要注意的是,它不能一边遍历一边删除,普通for循环和迭代器自身的remove()的可以。集合嵌套之List嵌套List,泛型可以用代入法替换。