学习任务:

视频学习

阅读文档理解需求

动手实现限定类型

动手测试

很多时候会根据课程的id查询课程信息、根据学生id查询学生信息,此时在泛型接口中定义T getById(long id),如下 :

package com.pbteach.javase.oop.generictypes4;

/**
 * 泛型接口测试
 * @author 攀博课堂
 * @version v1.0
 */
public interface PbList<T> {
	
	//添加元素
	int add(T obj);
	//根据索引获取元素
	T getByIndex(int index); 
	//根据id查询元素
	T getById(long id);
}

编写课程服务类,它实现了此接口,此服务类支持PbCourse及它的子类,代码如下:

package com.pbteach.javase.oop.generictypes4;

/**
 * 课程服务类
 * 需求:支持PbCourse类及它的子类
 * @author 攀博课堂
 * @version v1.0
 */
public class PbCourseList<T> implements PbList<T> {
	// 数组用于存储各种对象
	private static Object[] objects;

	public PbCourseList(int size){
			objects = new Object[size];
		}

	/**
	 * 添加课程
	 * 
	 * @param obj
	 * @return
	 * @author 攀博课堂
	 * @version v1.0
	 */
	@Override
	public int add(T obj) {
		for (int i = 0; i < objects.length; i++) {
			if (objects[i] == null) {
				// 向objects存储元素
				objects[i] = obj;
				return 1;
			}
		}
		return 0;
	}

	/**
	 * 根据索引删除课程
	 * 
	 * @param index
	 * @return
	 * @author 攀博课堂
	 * @version v1.0
	 */
	@Override
	public T getByIndex(int index) {
		if(index>=0 && index<objects.length) {
			return (T) objects[index];
		}
		return null;
	}

	/**
	 * 根据id查询课程
	 * 
	 * @param id
	 * @return
	 * @author 攀博课堂
	 * @version v1.0
	 */
	@Override
	public T getById(long id) {
		for (int i = 0; i < objects.length; i++) {
			if (objects[i] != null) {
				T obj = (T) objects[i];
				if(obj.getId() == id) {
					return obj;
				}
			}
		}
		return null;
	}

}

getById方法编译报错:

image-20210216153313224

错误提示也比较明确,因为T是一个泛型变量,具体也不知道什么类型,所以getId()方法在T中没有定义。

使用限定类型可以解决上边的问题,限定类型即限定泛型的类型为某个类型或它的子类型,格式如下:

<泛型标识符 extends 接口或类名>
如果有多个限定类型中间用&分隔
<泛型标识 extends 类名 & 接口 & 接口..>
当有多个限定类型时,只能有一个类且必须在最前边

更改PbCourseList类的定义代码如下:

package com.pbteach.javase.oop.generictypes4;

/**
 * 课程服务类
 * 需求:支持PbCourse类及它的子类
 * @author 攀博课堂
 * @version v1.0
 */
public class PbCourseList<T extends PbCourse> implements PbList<T> {
...

T extends PbCourse表示限定T为PbCourse及它的子类型。

完整的代码如下:

package com.pbteach.javase.oop.generictypes4_1;

/**
 * 课程服务类
 * 需求:支持PbCourse类及它的子类
 * @author 攀博课堂
 * @version v1.0
 */
public class PbCourseList<T extends PbCourse> implements PbList<T> {
	// 数组用于存储各种对象
	private Object[] objects;

	public PbCourseList(int size){
			objects = new Object[size];
		}

	/**
	 * 添加课程
	 * 
	 * @param obj
	 * @return
	 * @author 攀博课堂
	 * @version v1.0
	 */
	@Override
	public int add(T obj) {
		for (int i = 0; i < objects.length; i++) {
			if (objects[i] == null) {
				// 向objects存储元素
				objects[i] = obj;
				return 1;
			}
		}
		return 0;
	}

	/**
	 * 根据索引删除课程
	 * 
	 * @param index
	 * @return
	 * @author 攀博课堂
	 * @version v1.0
	 */
	@Override
	public T getByIndex(int index) {
		if(index>=0 && index<objects.length) {
			return (T) objects[index];
		}
		return null;
	}

	/**
	 * 根据id查询课程
	 * 
	 * @param id
	 * @return
	 * @author 攀博课堂
	 * @version v1.0
	 */
	@Override
	public T getById(long id) {
		for (int i = 0; i < objects.length; i++) {
			if (objects[i] != null) {
				T obj = (T) objects[i];
				if(obj.getId() == id) {
					return obj;
				}
			}
		}
		return null;
	}

}

T extends PbCourse表示限定T为PbCourse及它的子类型,测试时分别添加PbCourse及它的子类型PbCourseGeneral进行测试。

/**
 * 
 */
package com.pbteach.javase.oop.generictypes4_1;

/**
* 课程信息
* @author 攀博课堂
* @version v1.0
*/
public class PbCourse {
	
	//课程编号
	private long id;
	
	//课程名称
	private String courseName;
	
	//课程价格
	private float price;
	
	public PbCourse() {
		
	}
	public PbCourse(long id,String courseName,float price) {
		this.id = id;
		this.courseName = courseName;
		this.price = price;
	}

	...

}

/**
 * 
 */
package com.pbteach.javase.oop.generictypes4;

/**
* 普通课程信息
* @author 攀博课堂
* @version v1.0
*/
public class PbCourseGeneral extends PbCourse {
	
	
	public PbCourseGeneral() {
		super();
	}
	public PbCourseGeneral(long id,String courseName,float price) {
		super(id,courseName,price);
	}

	

}

测试代码如下:

package com.pbteach.javase.oop.generictypes4;


/**
 * 课程服务类
 * 需求:支持PbCourse类及它的子类
 * @author 攀博课堂
 * @version v1.0
 */
public class PbCourseList<T extends PbCourse> implements PbList<T> {
	...
	public static void main(String[] args) {
		PbCourseList<PbCourse> courseList = new PbCourseList<PbCourse>(10);
		courseList.add(new PbCourse(101L, "攀博课堂 java面向对象编程高级篇v1.0", 20F));
		courseList.add(new PbCourse(102L, "攀博课堂 Spring Cloud 微服务开发v1.0", 50F));
		PbCourse course = courseList.getById(101L);
		System.out.println(course);
		
		PbCourseList<PbCourseGeneral> courseList2 = new PbCourseList<PbCourseGeneral>(10);
		courseList2.add(new PbCourseGeneral(101L, "攀博课堂 免费课程java面向对象编程高级篇v1.0", 20F));
		courseList2.add(new PbCourseGeneral(102L, "攀博课堂 免费课程Spring Cloud 微服务开发v1.0", 50F));
		PbCourse course2 = courseList2.getById(101L);
		System.out.println(course2);
	}
提问-攀博课堂
我要提问 不会就问,有效沟通
关注公众号,加入微信群交流提问。 攀博课堂官方公众号
问答列表,查看本知识点所有问题