java参数传入的是一个类名_Java编程细节——泛型的定义(类、接口、对象)、使用、继承...

1. 设计泛型的初衷:

1) 主要是为了解决Java容器无法记忆元素类型的问题:

i. 由于Java设计之初并不知道会往容器中存放什么类型的元素,因此元素类型都设定为Object,这样就什么东西都能放了!

ii. 但是这样设计有明显的缺点:

a. 取出元素的时候必须进行强制类型转换(尽管集合在运行时里面元素的“运行时类型”不变,即元素的getClass返回的还是最初自己的类型而不是Object);

b. 如果不小心往集合里加了不相同类型的元素可能会导致类型异常(进行equals、compare比较的时候尤为明显);

c. 由于没有类型就需要在很多地方进行强制类型转换,但是这样做增加了编程的复杂度,并且代码也不美观(臃肿),维护起来也更加困难;

2) 泛型的概念定义:

i. 从Java 5开始,引入了参数化类型(Parameterized Type)的概念,改造了所有的Java集合,使之都实现泛型,允许程序在创建集合时就可以指定集合元素的类型,比如List就表名这是一个只能存放String类型的List;

ii. 泛型(Generic):就是指参数化类型,上面的List就是参数化类型,因此就是泛型,而String就是该List泛型的类型参数;

3) 泛型的好处:

i. 使集合可以记住元素类型,即取出元素的时候无需进行强制类型转化了,可以直接用原类型的引用接收;

ii. 一旦指定了性参数那么集合中元素的类型就确定了,不能添加其他类型的元素,否则会直接编译保存,这就可以避免了“不小心放入其他类型元素”的可能;

iii. 上述保证了如果在编译时没有发出警告,则在运行时就一定不会产生类型转化异常(ClassCastException);

iv. 显然,泛型使编程更加通用,并且代码也更加简洁,代码更加容易维护;

2. 创建泛型对象——自动类型推断的菱形语法:

1) 首先,定义泛型引用一定要使用尖括号指定类型参数,例如:List list、Map等,其中的String、Integer之类的就是类型参数;

2) 其次,使用构造器构造泛型对象的时候可以指定类型参数也可以不指定,例如:

i. List list = new List(); // 这当然是对的

ii. List list = new List<>(); // 这样对,因为List的类型参数可以从引用推断出!!!但是引用的类型参数是一定要加的,否则无法推断;

3) 由于<>很像菱形,因此上面的语法也叫做菱形语法;

4) 错误提示:引用无类型参数但构造器有类型参数的写法是不对的!例如,List list = new List();!!至于为什么不对,这会在泛型原理的章节中详细介绍,这里先记住这样写不对就行了!!反正就是一个原则,泛型引用是一定要指定类型参数的!!

5) 示例:af1d0c76445a8eb2275500cb6284c08c.png

3. 定义泛型类、接口:

1) 不仅Java的集合都定义成了泛型,用户自己也可以定义任意泛型的类、接口,只要在定义它们时用<>来指定类型参数即可;

2) 例如:public class Fruit { ... },其中指定了该泛型的类型参数,这个T是一个类型参数名,用户可以任意命名(就像方法参数的形参名一样),只有在定义该泛型的对象时将T替换成指定的具体类型从而产生一个实例化的泛型对象,例如:Fruit fruit = new Fruit<>(...);

3) 类型形参可以在整个接口、类体内当成普通类型使用,集合所有可使用普通类型的地方都可以使用类型形参,例如:773898fe525d2e30d0bcf11aaf4860f0.png

可以看到,在接口内/类体内甚至还可以使用该类型形参运用泛型!例如上面makeSet方法返回一个泛型Set;

4) 定义泛型构造器:泛型的构造器还是类名本身,不用使用菱形语法,例如:6aa8d8e165d7bdde1803316e9af2a35b.png

定义构造器无需MyGeneric(...) { ... }了,只有在new的时候需要用到菱形语法;

4. 实现/继承泛型接口/泛型类:

1) 定义泛型和使用泛型的概念:主要区别就是定义和使用

i. 那Java的方法做类比,Java的方法在定义的时候使用的都是形参(虚拟参数),但是在调用方法(使用方法)的时候必须传入实参;

ii. 同样泛型也有这个特点,泛型的类型参数和方法的参数一样,也是一种参数,只不过是一种特殊的参数,用来表示未知的类型罢了;

iii. 因此,泛型也是在定义的时候必须使用形参(虚拟参数,用户自己随意命名),但是在使用泛型的时候(比如定义泛型引用、继承泛型)就必须使用实参,而泛型的实参就是具体的类型,像String、Integer等具体的类型(当然也可以是自定义类型);

2) 泛型定义的时候使用形参,例如:public class MyGeneric { ... } // T就是一个自己随意命名的类型形参

3) 使用泛型的时候必须传入实参:

i. 定义引用(对象)的时候毫无疑问,肯定需要传实参:ArrayList list = ...; // 必须用具体的类型,像这里就是String来代替形参,即实参

ii. 实现/继承一个泛型接口/类的时候:

你在实现/继承一个接口/类的时候实际上是在使用该接口/类,比如:public class Son extends Father { ... }中Father这个类就是正在被使用,毫无疑问,必定是在使用;

因此泛型其实无法继承/实现,因为在实现/继承的时候必须为泛型传入类型实参,给定实参后它就是一个具体的类型了,就不再是泛型了

示例:public class MyType extends MyGeneric { ... } // implements、extends的时候必须传入类型实参,因为实在使用泛型。原则上,任何编程语言都不允许泛型模板层层继承!!

4) 继承之后,父类/接口中的所有方法中的类型参数都将变成具体的类型,你在子类中覆盖这些方法的时候一定要用具体的类型,不能继续使用泛型的类型形参了,例如:c4c40528685faca9bc674c11b5b07786.png

这一定能保证,这三个方法都是从父类中继承来的,只不过类型形参T被实例化成了String;

5. 泛型参数继承:

1) 上面派生出来的类不是泛型,是一个实体类型,因为其继承的泛型是具有类型实参的,而Java还支持一种特殊的语法,可以让你从泛型继续派生出泛型,而泛型的类型参数可以继续传承下去;

2) 语法如下:e94ee3ff7ae8a467494c7ef67ca2226c.png

即子泛型可以传承父泛型的泛型参数,那么在子类中泛型参数T就和父类的完全相同,还是照常使用(和父类一样正常使用);

3) 注意:

i. 这里extends Father了,因此父类泛型Father就是被使用了,而按照之前讲的规则,使用给一个泛型是必须要指定类型实参的!因此这里的这个语法是一种特殊语法,Java专门为这种语法开了后门,这种语法只有在类型参数传承的时候才会用到(即上面这种应用);

ii. 一旦使用了这种语法,就表示要进行类型参数的传承了(即父类的T传递给子类继续使用,因此子类也是一个跟父类一样的泛型);

iii. 并且一旦使用了这种语法,那么子类定义中的Son和extends Father中的类型参数必须和定义父类时的类型参数名完全一样!!

a. 以下三种情况全部错误(全部发生编译报错):8ea9fe7dace25d4da4906440905bdc3c.png

必须全部使用和父类定义相同的类型参数名(T)!才行,这是Java语法的特殊规定;

4) 其实Java容器中很多类/接口都是通过类型参数传承来定义的:

i. 最典型的例子就是:public interface List extends Collection { ... }

ii. 虽然"如果A是B的父类,但Generic不是Generic"的父类,但"如果A是B的父类,那A一定是B的父类"!这是一定的;

iii. 因为类型参数传承的定义方式本身就是:Son extends Father,那Father一定是Son的父类咯!

6. 在使用泛型的时候可以不使用菱形语法指定实参,直接裸用类型名:

1) 例如:

i. 定义引用(对象)时裸用类名:ArrayList list = new ArrayList(); // 当然也可以写成ArrayList list = new ArrayList<>();

ii. 实现/继承:public class MyType extends MyGeneric { ... }

上面使用的类型或者接口在定义的时候都是泛型!!但是使用它们的时候忽略类型参数(都不用加菱形);

2) Java规定,一个泛型无论如何、在任何地方、不管如何使用,它永远都是泛型,因此这里既是你忽略类型实参它底层也是一个泛型,那么它的类型实参会是什么呢?既然我们没有显式指定,那么Java肯定会隐式为其指定一个类型实参吧?

3) 答案是肯定的,如果使用泛型的时候不指定类型实参,那么Java就会用该泛型的“原生类型“来作为类型实参传入,那么“原生类型“是什么呢?这里先不介绍,会在下一章的”泛型原理“里详细分解;但是我们这里可以先透露一下,Java集合的原生类型基本都是Object,因此像上面的ArrayList list = new ArrayList();写法其实传入的是Object类型实参,即ArrayList!0f6f55bed80c38e67fc79f8e4bc277da.png

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/399143.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

ExtJS Grid Column Number

{xtype: numbercolumn,text: 亏盈数量,width: 130,dataIndex: LossOrProfitNum,editor: {xtype: numberfield,minValue: 0,decimalPrecision: 2},renderer: function (value, cellmeta) {return Ext.util.Format.number(value, 0.00);}}转载于:https://www.cnblogs.com/denghua…

#define | enum(enumerator)

/***************************************************************************** #define | enum(enumerator)* 声明&#xff1a;* 今天突然在Linux内核看到枚举和宏&#xff0c;感觉是一样的功能&#xff0c;于是找了一下他们* 之间差异。** …

网页制作中如何自定义网页图标

第一步&#xff0c;准备一个图标制作软件。 首先您必须了解所谓的图标&#xff08;Icon&#xff09;是一种特殊的图形文件格式&#xff0c;它是以.ico 作为扩展名。普通的图像设计软件无法使用这种格式&#xff0c;所以您需要到下载一个ico图标工具,本站常用软件既有,推荐强大…

ext 解析后台返回response.responseText中的数据

Ext.Ajax.request({ url: "...", method: "POST", params: { currentID: mainNode.attributes.id }, success: function (response) { var resp Ext.decode(response.responseText )&#xff1b; resp.totalCount; } }); //ajax over //响应中返回的resp…

java资源争夺_所有满足类似需求,争夺同类资源的组织和个人统称为(   )。...

【判断题】重合断面的轮廓线用细实线绘制。【单选题】阿萨德法师法啥【单选题】三相桥式交叉连接电路为限制脉动环流需要( )平衡电抗器【单选题】地方搞活动风格化大发光火【填空题】若s是int型变量,且s6,则表达式s%2(s1)%2的值为________。【填空题】负反馈的作用是( )。【单选…

Linux环境下安装部署AWStats日志分析系统实例

AWStats是使用Perl语言开发的一款开放性日志分析系统&#xff0c;可分析Apache网站服务器的访问日志&#xff0c;还可以用来分析Samba、Vsftpd、IIS等日志信息。此文章主要讲解如何在linux系统下安装部署关于对Apache网站服务站日志分析的AWStats。实验步骤一&#xff0c;安装部…

HDU4911 Inversion 解题报告

题意&#xff1a;求逆序对 解题思路&#xff1a;1)树状数组 离散化 解题代码&#xff1a; 1 // File Name: a.cpp2 // Author: darkdream3 // Created Time: 2014年08月05日 星期二 12时05分09秒4 5 #include<vector>6 #include<list>7 #include<map>8 #inc…

springmvc的国际化

1&#xff1a;三个国际化资源文件 i18n.usernameUsername i18n.passwordPassword i18n.username\u7528\u6237\u540D i18n.password\u5BC6\u7801 i18n.usernameUsername i18n.passwordPassword 2&#xff1a;在spring中配置国际化资源文件 <!-- 配置国际化资源文件 --><…

java逻辑编程题_50道经典Java逻辑编程题白岩山

光棍节英语-2021年1月21日发(作者&#xff1a;卞敏)【程序1】题目&#xff1a;古典问题&#xff1a;有一对兔子&#xff0c;从出生后第3个月起每个月都生一对兔子&#xff0c;小兔子长到第三个月后每个月又生一对兔子&#xff0c;假如兔子都不死&#xff0c;问每个月的兔子总数…

.9-浅析webpack源码之NodeEnvironmentPlugin模块总览

介绍Compiler的构造比较无趣&#xff0c;不如先过后面的&#xff0c;在用到compiler的时候再做讲解。 这一节主要讲这行代码&#xff1a; // 不管这里 compiler new Compiler(); compiler.context options.context; compiler.options options; // 看这里 new NodeEnvironmen…

运行QQ出现initialization failure 0x0000000c错误和浏览器上不了网

出现QQ出现initialization failure 0x0000000c错误和浏览器上不了网的问题&#xff0c;原因是关机的时候没有正常关闭导致的。 解决方法&#xff1a; 1、我们在开始菜单栏中的附件中找到“命令提示符”&#xff0c;然后点击右键选择“以管理员身份运行”。 或者windowx&#xf…

Unity3D 动态加载 图片序列正反播放

参考来源 跟来源的电子图书翻页多了点细节上的变化。 using UnityEngine; using System.Collections; using System.Resources;public class MovePic : MonoBehaviour {public Texture2D[] texAll; //图片序列储存的图片组&#xff0c;注意需要定义这个组的size大小为图片序列…

【IT笔试面试题整理】寻找二叉树两节点的最近的公共祖先

【试题描述】 求二叉树中任意两个节点的最近公共祖先也称为LCA问题&#xff08;Lowest Common Ancestor&#xff09;。 二叉查找树 如果该二叉树是二叉查找树&#xff0c;那么求解LCA十分简单。 基本思想为&#xff1a;从树根开始&#xff0c;该节点的值为t&#xff0c;如果t大…

解释spring,struts,hibernate优缺点

解释spring,struts,hibernate优缺点 Struts优点&#xff1a;对视图层进行封装 更好的分离视图层和控制层 对数据进行封装 缺点: 1 、转到展示层时&#xff0c;需要配置forward&#xff0c;每一次转到展示层&#xff0c;相信大多数都是直接转到jsp&#xff0c;而涉及到转向&…

java单例模式的七种写法_Java设计模式之单例模式的七种写法

什么是单例模式&#xff1f;单例模式是一种常见的设计模式&#xff0c;单例模式的写法有很多种&#xff0c;这里主要介绍三种&#xff1a; 懒汉式单例模式、饿汉式单例模式、登记式单例 。单例模式有以下特点&#xff1a;1、单例类只能有一个实例。2、单例类必须自己创建自己唯…

在Hadoop集群上,搭建HBase集群

(1)下载Hbase包,并解压:这里下载的是0.98.4版本,对应的hadoop-1.2.1集群 (2)覆盖相关的包:在这个版本里,Hbase刚好和Hadoop集群完美配合,不需要进行覆盖. 不过这里写了个覆盖的脚本,可以留着备用. find -name hadoop*jar | sed s/2.2.0/2.3.0/g | sed s/.\///g > f.log rm .…

java js跳出循环_[Java教程]js循环的总结

[Java教程]js循环的总结02016-10-07 15:00:14js原生的循环有两种&#xff0c;一般的for循环和for...in循环。还有一种常用jQuery.each()循环。一. js原生循环a. for循环&#xff0c;代码如下&#xff1a;var myArray [1,2,3];for (var i 0; i < myArray.length; i) {conso…

Beta版本冲刺

1.凡事预则立&#xff0c;在Beta开始前&#xff0c;以小组为单位&#xff0c;在敏捷冲刺前发布一篇博客&#xff0c;描述&#xff1a; a. 下一阶段需要改进完善的功能&#xff1a; 无 b. 下一阶段新增的功能 修改密码功能 管理员功能 生成表格的优化 c. 需要改进的团队分工&…

Struts2国际化

一&#xff1a;简单理解 国际化简称i18n&#xff0c;其来源是英文单词 internationalization的首末字符i 和n。18为中间的字符数。 随着全球经济的一体化&#xff0c;软件开发者应该开发出支持多国语言、国际化的Web应用。对于Web应用来说&#xff0c;同样的页面在不同的语言环…

NOI经验谈

对于NOI来说&#xff0c;甚至比硬实力更加重要。我觉得一场考试这么几件事要做&#xff1a;看题&#xff0c;选题&#xff0c;分析&#xff0c;编码&#xff0c;调试&#xff0c;测试&#xff0c;骗分。 1、看题 拿到试卷以后的第一件事就是看题。看题不是看小说&#xff0c;要…