J2SE5.0新特性之范型编程

6、 实时家禽健康识别与疾病检测系统的深入解析 本文深入解析了一种基于物联网的实时家禽健康识别与疾病检测系统,结合图像分析和音频分析技术,能够有效识别病鸡并防止疾病传播。文章详细介绍了系统的测试环境、数据采集与预处理方法、图像与音频分析流程,并对系统性能进行了全面评估。最后提出了未来改进方向,包括多模态融合、深度学习应用及实时性优化等。 阅读详情
本章主要参考sun公司文档。

 

C++程序员对范型编程肯定不陌生,尤其在STL大行其道的时候,C#2.0也将实现范型编程的功能。Java也不甘示弱,也推出了范型编程的语言新特性。

 

1.一个简单的范型示例

在以前,你可能遇到过这样的代码:
  1. List list = new LinkedList();
  2. list.add(“麻省理工”);
  3. list.add(“普林斯顿”);
  4. list.add(“伯克利”);
  5. String name = (String)list.iterator.next();
  6.  


注意,第三行需要强制转换。而使用范型:
  1. List<String> list = new LinkedList<String>();
  2. list.add(“麻省理工”);
  3. list.add(“普林斯顿”);
  4. list.add(“伯克利”);
  5. String name = list.iterator.next();
  6.  

这里将list声明成String类型的List。List是有一个类型参数的范型接口。这个例子中类型参数是String。

 

2.定义简单的范型

看j2se5.0中List和Iterator接口的实现(片断):
  1. public interface List<E> 
  2. { 
  3. void add(E x);
  4. Iterator<E> iterator();
  5. }
  6. public interface Iterator<E> 
  7. { 
  8. E next();
  9. boolean hasNext();
  10. }
  11.  
  12.  

上面的代码我们比较熟悉,但是其中增加了尖括号。尖括号中的内容定义了接口List和Iterator的形式类型参数。类型参数可以用在范型声明中,如类和接口的声明。

一旦声明了范型,你就可以使用它。在上面的例子中使用了List<String>。这里使用String是实参,代替了形参E。如果使用List<Integer>,则用实参Integer代替了形参E。

不管List<Integer>还是List<String>,它们的类只有一个。考虑下面的代码:
  1. List<String> list1 = new LinkedList<String>();
  2. List<Integer> list2 = new LinkedList<Integer>();
  3. System.out.println(list1.getClass()==list2.getClass());
 

输出结果为true。

 

一般来说,形式类型参数都是大写,尽量使用单个字母,许多容器类都使用E作为参数。

 

3.范型和继承

考虑下面的代码,你认为它会出错吗?
  1. String s = “smallnest@163.com”;
  2. Object o = s:
  3.  

当然,String类继承Object类,这样做不会出错。但下面的代码呢?
  1. List<String> s = new LinkedList<String>();
  2. List<Object>o=s;
  3.  


编译出错!

是的,List<Object>和List<String>没有继承关系。

 

4.通配符

考虑下面一个方法:
  1. public void printCollection(Collection<Object> c)
  2. {
  3.    for(Object o:c)
  4. {
  5.    System.out.printf(“%s%n”,o);
  6. }
  7. }
  8.  

事实上,上面这个方法并不通用,它只能打印Collection<Object>类型的集合,象其他的如Collection<String>、Collection<Integer>并不能被打印,因为对象类型不一致。

为了解决这个问题,可以使用通配符:
  1. public void printCollection(Collection<?> c)
  2. {
  3.    for(Object o:c)
  4. {
  5.    System.out.printf(“%s%n”,o);
  6. }
  7. }
  8.  

Collection<?>被称作未知类型的集合。问号代表各种类型。

上面的读取集合中的数据时,我们采用Object类型。这样做时可以的,因为不管未知类型最终代表何种类型,它的数据都继承Object类,那么再考虑一下下面的代码:
  1. Collection<?> c = new ArrayList<String>();
  2. c.add(new Object());  //!!!!
  3.  

这样做时错误的,因为我们不知道?代表何种类型,所以我们不能直接将Object增加到集合中,这会出现类型不匹配的情况。

 

5.有限制的通配符

考虑下面的代码
  1. class Man
  2. {
  3.    public String name = “”;
  4. }
  5. class GoodMan extends Man
  6. {
  7.    public String name = “”
  8. }
  9. class BadMan extends Man
  10. {
  11.    public String name = “”
  12. }
  13.  
  14.  

考虑下面的范型方法:
  1. public void printName(List<Man> men)
  2. {
  3.    for(Man man:men)
  4.    {
  5.       System.out.println(“姓名:” + man.name);
  6.    }
  7. }
  8.  


这个范型方法只能显示List<Man>类型的数据,下面的代码允许显示Man和它的子类。
  1. public void printName(List<? extends  Man> men)
  2. {
  3.    for(Man man:men)
  4.    {
  5.       System.out.println(“姓名:” + man.name);
  6.    }
  7. }
  8.  

这里使用? extends Man代替Man,表明接受任何Man的子类做为参数。

和前面的代码类似,下面的代码也是不正确的:
  1. public void adman(List<? extends Man> men)
  2. {
  3.    GoodMan good = new GoodMan();
  4.    good.name = “晁岳攀”;
  5.    men.add(good);
  6. }
  7.  

原因也很简单,因为?代表一切继承Man的类,你并不能保证就一定时GoodMan类。

 

和这种用法类似:
  1. public void adman(List<? super GoodMan> men)
  2. {
  3.    GoodMan good = new GoodMan();
  4.    good.name = “晁岳攀”;
  5.    men.add(good);
  6. }
  7.  
  8.  

6.范型方法

考虑下面的代码,我们将一个数组的内容加到一个集合中
  1. public  void copyArrayToCollection(Man[] men, Collection<?>c)
  2. {
  3. for(Man man:men)
  4. {
  5.    c.add(man);
  6. }
  7. }
  8.  

这段代码时错的!

因为我们并不知道集合C的类型,所以不能将Man类型的数据加到集合中。

可以使用范型方法解决:
  1. public <T> void copyArrayToCollection(T[] men, Collection<T>c)
  2. {
  3. for(T man:men)
  4. {
  5.    c.add(man);
  6. }
  7. }
  8.  
  9.  

这里T时一个形式类型参数。

何时该采用通用方法?何时该采用通配符?

考虑下面的例子:
  1. interface  Collection<E>
  2. {
  3.   public boolean containsAll(Collection<?> c);
  4. public boolean addAll(Collection<? extends E> c);
  5. }
  6.  

改写成通用方法
  1. interface  Collection<E>
  2. {
  3.    public <T> boolean containsAll(Collection<T> c);
  4. public <T extends E> boolean addAll(Collection<T> c);
  5. }
  6.  

然而,在这里每个方法T只使用了一次,返回值不依赖形式参数,其他参数也不依赖形式参数。这说明实参被用作多态,这种情况下就应该用通配符。
YOLOv11 损失函数解析 YOLOv11 在 YOLO 系列的持续演进中,通过 ​多模态损失协同优化、动态任务感知机制 和 ​超轻量化设计,实现了检测精度与推理效率的再突破。其损失函数设计融合了前沿的几何建模、分布学习与自监督技术,显著提升了复杂场景下的鲁棒性。 阅读详情

相关推荐

[VisionPro] CogPMAlignTool 工具详解

[VisionPro] [CogPMAlignTool] [模板匹配]

weixin_43163656的博客 1万+

Java泛型方法

Java泛型方法

qiao代码的木偶人的博客 1万+

时序分析28 - 时序预测 格兰杰因果关系(中) python实践1

时序分析28 - 时序预测 - 格兰杰因果关系(中) Python 实践 1 上一篇文章我们介绍了格兰杰因果关系的基本概念、背景以及相关统计检验法。本篇文章我们使用Python编程实践一下。 实践1:股票价格数据之间的格兰杰因果关系 问题:苹果公司今天的股价是否可以用来预测明天的特斯拉的股价? 数据:来自雅虎财经 import matplotlib.pyplot as plt import seaborn as sns import numpy as np import pandas as pd 读入数据

weixin_43171270的博客 8837

Java 泛型详解(超详细的java泛型方法解析)

超详细的java泛型方法解析

qq_66912832的博客 1万+

解决倍福ADS通信错误1861和6:一次完整的TwinCAT3路由配置与故障排查实录

本文详细解析了在Linux系统上解决倍福ADS通信错误1861和6的完整流程,包括TwinCAT3路由配置与故障排查。通过实例演示了如何正确配置AMS NetID、使用adstool工具添加静态路由,以及高级网络抓包分析技巧,帮助工程师快速定位和解决通信问题。

weixin_30875157的博客 523

Proteus仿真实战:ADC0832时序解析与51单片机精准电压采集

本文详细解析了ADC0832模数转换芯片在Proteus仿真环境中的时序控制与51单片机驱动实现。通过实战代码示例和精度优化技巧,帮助开发者掌握电压采集的关键技术,包括时序配置、数据校验和噪声抑制等核心要点,提升嵌入式系统设计的精准度与可靠性。

weixin_29172963的博客 873

Java泛型方法和泛型参数之美

使用泛型的好处:1.提升了程序的健壮性和规范性2.编译时,检查添加元素的类型,提高了安全性3.减少了类型转换的次数,提高效率。

在青海看海的企鹅的博客 1830

BIOS更新后PIN不可用怎么办?从原理到实操的完整修复指南

在计算机维护中,BIOS更新是常见的固件升级操作,但其引发的登录异常却常让用户措手不及。Windows Hello PIN并非传统密码,它通过TPM芯片与设备启动环境(PCR状态)强绑定,一旦主板固件或安全启动配置改变,TPM便会拒绝释放密钥,导致“由于此设备上的更改,你的PIN不再可用”。理解这一原理后,恢复路径清晰可控:优先尝试密码登录,或通过WinRE替换utilman.exe创建临时管理员,必要时还需处理BitLocker恢复密钥。本文面向系统维护与数据安全场景,系统梳理PIN失效的恢复流程与避坑方

weixin_31364787的博客 386

java 泛型详解-绝对是对泛型方法讲解最详细的,没有之一

对java的泛型特性的了解仅限于表面的浅浅一层,直到在学习设计模式时发现有不了解的用法,才想起详细的记录一下。 本文参考java 泛型详解、Java中的泛型方法、 java泛型详解 1. 概述泛型在java中有很重要的地位,在面向对象编程及各种设计模式中有非常广泛的应用。什么是泛型?为什么要使用泛型? 泛型,即“参数化类型”。一提到参数,最熟悉的就是定义方法时有形参,然后调用此方法时传

s10461的博客 62万+

Linear超高PSRR线性稳压器-典型应用电路解析

本文整理完了LT3045数据手册内所有的典型应用电路,试图让沉默的电路开口,简单介绍了他们这样做的目的和原理,从中我们可以更加熟悉这颗经典芯片的应用。但也有一些电路并没有搞懂,遗留下了不少问题。

硬件工程师笔记 2945

Unity机械拆装实战:5步搞定发动机模型交互式装配(附完整代码)

本文详细介绍了在Unity中实现高交互性机械拆装仿真的完整流程。以发动机模型为例,通过5个核心步骤:项目初始化与模型准备、核心交互实现、智能装配逻辑、场景管理与相机控制、进阶优化与扩展,系统讲解了从零构建交互式装配功能的方法,并提供了完整的代码示例。

weixin_28049429的博客 217

J2SE5.0新特性

[1]J2SE5.0新特性之静态导入J2se5.0之前,如果需要使用其他类的静态方法,如java.lang.Math中的方法,需要写以下的代码:double value = Math.log(100)*Math.PI; 现在你只需在静态导入,然后就可以直接在代码中使用静态方法和静态字段:import static java.lang.Math.*;…double value = log(100

Jerome Kwok网络日志 1044

uniapp [安卓苹果App端] - 实现APP开发后台保活+息屏后台持续运行效果,强制后台保活手机黑屏后进程存活后台保持网络连接或持续定位等功能提供支持(app后台运行休眠仍然可以确保一直运行)

uniapp APP开发后台保活,Uniapp-APP后台保活插件(安卓苹果ios后台保活)保证应用在后台继续运行,uniapp实现app保活 保后台运行 避免系统主动杀进程,如何让安卓APP一直在后台运行?uniapp 安卓 APP 后台持续运行(保活)iOS App后台保活,Android 后台运行白名单实现保活,保活息屏后台运行,uniapp后台保活,uniapp熄屏 后台运行,Android/ios进程保活/息屏后后台保持定位、网络运行,uniapp在android ios保活,挂后台可运行,安卓A

🏆 前端领域优质创作者 1万+

J2SE5.0新特性之自动装箱解箱

J2SE5.0新特性之自动装箱解箱晁岳攀 smallnest@163.com 作为一个程序员,一个java程序员,在使用Map和Collection的时候,经常回遇到下面的情况:       Map map;       …       String name = map.get(“name”);…这里从map对象取出的值,需要强制转换成我们所需要的类型,这种情况在

鸟窝 1472

Outlook Express 6 (OE6) for Win7/Win8/Win10

英文版 Outlook Express6.0, 兼容Win7/Win10/WinXP,解压就可用。

pscad IEEE标准系统搭建说明

pscad IEEE标准系统搭建说明,包含典型的IEEE 9节点、14节点、30节点、39节点和118节点系统。内含标准测试系统的原始数据和潮流结果。

在 Eclipse 3.1 中体验 J2SE 5.0 的新特性: 第三部分 :范型

邹青 (qingzou@cn.ibm.com), 软件工程师, IBM 中国软件开发中心普及运算部门吴嫣 (wuyan@cn.ibm.com), 软件工程师, IBM 中国软件开发中心普及运算部门吴疆 (wujiangj@cn.ibm.com), 软件工程师, IBM 中国软件开发中心普及运算部门2005 年 7 月 01 日本文将介绍J2SE 5.0中三个比较重要的特性: 枚举类型, 注

sdbany的专栏 828

jdk-8u144-linux-x64.tar.gz.

该资源为搭建Linux系统Java环境用,资源的后缀为tar.gz格式的压缩包

[转载]在 Eclipse 3.1 中体验 J2SE 5.0 的新特性: 第三部分 :范型

在 Eclipse 3.1 中体验 J2SE 5.0 的新特性: 第三部分 :范型本文将介绍J2SE 5.0中三个比较重要的特性: 枚举类型, 注释类型, 范型, 并在此基础上介绍在如何在Eclipse 3.1开发环境中开发枚举...

congji3817的博客 167

锂电池充电器电路设计 里面有电路

锂电池充电器电路设计 里面有电路 3.7V升压到5V电路设计。

在JBuilder中使用J2SE 5.0新特性

 1、安装J2SE 5.0JBuilder2006之前的版本需要首先下载安装 J2SE 5.0(http://java.sun.com/j2se/1.5.0/download.jsp)JBuilder2006本身提供了对J2SE 5.0的支持,因此无需重新安装。2、配置路径  (1)Tools->Configure->JDKs->JDK home path 指定J2SE 5.0的安装路

幽客独往 2760

J2SE 5.0 新特性

The Tiger feature list is defined in JSR-176 (J2SE 5.0 (Tiger) Release Content), which serves as an umbrella JSR that only lists APIs defined in other component JSRs. Please see JSR-176 for details ab

设计模式空间 1313

J2SE 1.5版本的新特性一览

到了2003的年末,J2SE1.5的beta版本就将发布了。这次发布和现在已经发布的J2SE1.4的两个更新1.4.1和1.4.2都如2003年的JavaOne大会预期的发布。如果你没有参加这次大会,或者想重新回顾一下,那么下面就是这次大会的简要内容。J2SE 1.4.1 and 1.4.2 Releases当1.4.1(开发代号“Hopper”)在2002年9月发布以及它的后续版本1.4.2(开

1157

J2SE 5.0新特性

J2SE 5.0 (Tiger)的发布是Java语言发展史上的一个重要的里程碑, 是迄今为止在 Java 编程方面所取得的最大进步.    J2SE 5.0提供了很多令人激动的特性.这些特性包括范型(generics)的支持, 枚举类型(enumeration)的支持, 元数据(metadata)的支持, 自动拆箱(unboxing)/装箱(autoboxing), 可变个数参数(varargs)...

zhangyong_ok的博客 186

Sun公司的Java平台最新版本J2SE 5.0

100多个新特性使J2SE 5.0成为Java开发者的新一代平台    (2004年10月9日讯) Sun Microsystems公司正式发布Java 2平台标准版(J2SE™) 5.0版。作为通过JCPsm(Java Community Process sm)研发的最大规模的项目之一,有大约160位专家成员参与了J2SE 5.0版本的研发。J2SE 5.0提供了100多个新特性,为

首席技术执行官CTO(Chief Technology Officer)|技术总监--邓斌博客 2417
上一篇: J2SE5.0新特性之元数据
下一篇: 猛虎出山: Java 5.0的新语言特性
start_java
博客等级 码龄22年 5粉丝 84原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值