一. 泛型概念的提出(为什么需要泛型)?

首先,我们看下下面这段简短的代码:

//import java.util.List;

public class GenericTest {

    public static void main(String[] args) {
List list = new ArrayList();
list.add("语文");
list.add("数学");
list.add(100); //编译错误 for (int i = 0; i < list.size(); i++) {
String name = (String) list.get(i); //
System.out.println("name:" + name);
}
}
}

定义了一个List类型的集合,先向其中加入了两个字符串类型的值,随后加入一个Integer类型的值。这是完全允许的,因为此时list默认的类型为Object类型。在之后的循环中,由于忘记了之前在list中也加入了Integer类型的值或其他编码原因,很容易出现类似于//1中的错误。因为编译阶段正常,而运行时会出现“java.lang.ClassCastException”异常。因此,导致此类错误编码过程中不易发现。

在如上的编码过程中,我们发现主要存在两个问题:

1.当我们将一个对象放入集合中,集合不会记住此对象的类型,当再次从集合中取出此对象时,改对象的编译类型变成了Object类型,但其运行时类型任然为其本身类型。

2.因此,//1处取出集合元素时需要人为的强制类型转化到具体的目标类型,且很容易出现“java.lang.ClassCastException”异常。

那么有没有什么办法可以使集合能够记住集合内元素各类型,且能够达到只要编译时不出现问题,运行时就不会出现“java.lang.ClassCastException”异常呢?答案就是使用泛型。

二.什么是泛型?

泛型,即“参数化类型”。一提到参数,最熟悉的就是定义方法时有形参,然后调用此方法时传递实参。那么参数化类型怎么理解呢?顾名思义,就是将类型由原来的具体的类型参数化,类似于方法中的变量参数,此时类型也定义成参数形式(可以称之为类型形参),然后在使用/调用时传入具体的类型(类型实参)。

看着好像有点复杂,首先我们看下上面那个例子采用泛型的写法。

public static void main(String[] args) {

        List<String> list = new ArrayList<String>();//

        list.add("语文");
list.add("数学");
list.add("英语");
//list.add(100);//1 编译错误 //输出
for(int i=0 ; i<list.size();i++){
String subjectName = list.get(i);//
System.out.println("科目名称:"+subjectName); }
}

1. 程序//1处试图将一个Integer对象添加到list集合中,程序将无法通过编译,报出:
    java.lang.Error: Unresolved compilation problem
    因为list只接受String对象作为元素,所以//1处代码在编译时会得到错误提示

2.所以要使用泛型,如程序2处创建一个特殊的List集合:list,这个List集合只能保存字符串对象,不能保存其他类型的对象
   创建这种特殊集合的方式是:在集合接口、类后增加尖括号,尖括号里放一个数据类型,即表示这个集合接口、结合类只能保存特定类型的对象
   如//2处的类型声明,它指定:list不是一个任意的list,而是一个String类型的list,写作List<String>.我们认为list是带一个类型参数的泛型接口

3.程序在//3处不需要进行强制类型转换,因为list对象可以“记住”它的所有集合元素都是String类型

结合上面的泛型定义,我们知道在List<String>中,String是类型实参,也就是说,相应的List接口中肯定含有类型形参。且get()方法的返回结果也直接是此形参类型(也就是对应的传入的类型实参)。

三、JAVA 7泛型的“棱形”写法

在java 7以前,如果使用带泛型的接口、类定义变量,那么调用构造器创建对象时构造器的后面也必须带泛型,则显得有些多余,例如:

List<String> strList = new ArrayList<String>();
Map<String ,Interger> scores = new HashMap<String ,Integer>();

上面两条语句中的粗体代码部分是完全多余的,在java 7以前这是必需的,不能省略。java 7以后,只要给出一对尖括号(<>)即可,java可以
推断出尖括号里应该是什么泛型信息。即上面两条语句可以改为如下形式:

List<String> strList = new ArrayList<>();
Map<String ,Interger> scores = new HashMap<>();

因而简化代码:

List<String> list = new ArrayList<>();//

        list.add("语文");
list.add("数学");
list.add("英语");
//list.add(100);//2 //输出
for(int i=0 ; i<list.size();i++){
String subjectName = list.get(i);//
System.out.println("科目名称:"+subjectName); }

Double泛型:

   List<Double> list = new ArrayList<>();//

        list.add(10.1);
list.add(10.2);
list.add(10.3);
//list.add(100);//1 //输出
for(int i=0 ; i<list.size();i++){
Double subjectName = list.get(i);//
System.out.println("科目成绩:"+subjectName); }

键值对:

java中的map其实就是以键值对形式的存放数据的容器,其常用的实现类主要是哈希map
例如:
Map map = new HashMap();
插入元素:map.put("key", obj); 
移除元素: map.remove("key");
清空: map.clear();

import java.util.HashMap;
import java.util.Map;

Map<String,Double> list = new HashMap<>();//

        list.put("语文",10.1);
list.put("数学",10.1);
list.put("英语",100.0);
String arr[]={"语文","数学","英语"}; //输出
for(int i=0 ; i<list.size();i++){
Double subjectName = list.get(arr[i]);//必须是键值对
System.out.println("科目成绩:"+subjectName); }

java泛型简单学习的更多相关文章

  1. (一)关于java泛型的学习总结(泛型方法、泛型擦除)

    目录概要 一.泛型方法 二.利用泛型方法的特性实现代码的简化 三. 关于泛型的擦除 四.无界通配符和原生类型区别 五.转型和警告   泛型 一般的类中的属性或方法的参数,只能使用具体的类型:要么是基本 ...

  2. java clone简单学习

    最近在帮忙写单侧的时候,经常会和这几个对象类打交道,因为对java也不是很熟悉,刚好学习一下,都是很浅的学习,并没有深入的去学习哈,因为感觉也用不上. protected Object clone() ...

  3. Java泛型简单理解

    优点1: 没有使用泛型,向list集合中添加非字符串,运行时会报错:类型不匹配 ObjectList.java: package cn.nxl2018; import java.util.ArrayL ...

  4. Java注解简单学习

    注解(也被称作元数据)为我们在代码中添加信息提供了一种形式化的方法,使我们在稍后某个时刻可以很方便的使用这些数据,其在一定程度上将元数据与源代码文件结合在一起,而不是保存在外部文档中. 注解使我们可以 ...

  5. Java抽象类简单学习

    使用抽象类应该注意的几个要点: 包含一个或者多个抽象方法的类必须被声明为抽象类. 将类声明为抽象类,不一定含有抽象方法. 通常认为,在抽象类中不应该包括具体方法,建议尽量将通用的域和方法放在超类中. ...

  6. java 泛型简单使用

  7. Java学习笔记(二一)——Java 泛型

    [前面的话] 最近脸好干,掉皮,需要买点化妆品了. Java泛型好好学习一下. [定义] 一.泛型的定义主要有以下两种: 在程序编码中一些包含类型参数的类型,也就是说泛型的参数只可以代表类,不能代表个 ...

  8. Java泛型学习笔记 - (七)浅析泛型中通配符的使用

    一.基本概念:在学习Java泛型的过程中, 通配符是较难理解的一部分. 主要有以下三类:1. 无边界的通配符(Unbounded Wildcards), 就是<?>, 比如List< ...

  9. Java泛型学习笔记--Java泛型和C#泛型比较学习(一)

    总结Java的泛型前,先简单的介绍下C#的泛型,通过对比,比较学习Java泛型的目的和设计意图.C#泛型是C#语言2.0和通用语言运行时(CLR)同时支持的一个特性(这一点是导致C#泛型和Java泛型 ...

随机推荐

  1. POJ 3421 X-factor Chains

    线型素数筛+质因素分解+组合数. AC后发现这样做效率有点低..766ms. #include<stdio.h> #include<string.h> #include< ...

  2. Extjs4中的布局

    布局用于定义容器如何组织内部子元素和控制子元素的大小.在一个应用程序中,作为定义容器的组织形式,布局是一个十分重要的组件.是显示单个子元素?还是垂直或水平显示多个子元素?这些均由布局来定义.并且布局将 ...

  3. sql数据库中查询第几条到第几条的数据

    通用方法: select top 500 * from (select top 1000 * from UserSearchDatas order by ID) a order by ID desc ...

  4. mysql 常用指令

    修改表的字符集 88down voteaccepted If you want to change the table default character set and all character ...

  5. IM 融云 之 开发基础概念

    基础概念 - 开发篇 App Key / Secret App Key / Secret 相当于您的 App 在融云的账号和密码.是融云 SDK 连接服务器所必须的标识,每一个 App 对应一套 Ap ...

  6. Python3基础 用 while循环实现 斐波那契数列

    镇场诗: 诚听如来语,顿舍世间名与利.愿做地藏徒,广演是经阎浮提. 愿尽吾所学,成就一良心博客.愿诸后来人,重现智慧清净体.-------------------------------------- ...

  7. AForge.NET是一个专门为开发者和研究者基于C#框架设计的视频录像

    AForge.NET是一个专门为开发者和研究者基于C#框架设计的,他包括计算机视觉与人工智能,图像处理,神经网络,遗传算法,机器学习,模糊系统,机器人控制等领域.这个框架由一系列的类库组成.主要包括有 ...

  8. Eclipse和debug的一些快捷键

    F5单步调试进入函数内部.  F6单步调试不进入函数内部,如果装了金山词霸2006则要把“取词开关”的快捷键改成其他的.  F7由函数内部返回到调用处.  F8一直执行到下一个断点.  F11 这个好 ...

  9. js原生设计模式——7原型模式之new+call(this)组合应用再探讨实例

    <!DOCTYPE html><html lang="en"><head>    <meta charset="UTF-8&qu ...

  10. js原生设计模式——4安全的工厂方法模式之Factory方法模式

    <!DOCTYPE html><html lang="en"><head>    <meta charset="UTF-8&qu ...