`
nathan09
  • 浏览: 155524 次
  • 性别: Icon_minigender_1
  • 来自: 杭州
文章分类
社区版块
存档分类
最新评论

【读书笔记】TiJava——泛型

 
阅读更多

类型参数推断

•使用泛型类时,必须在创建对象时指定类型参数。
•使用泛型方法时,不需要指定类型参数。
•方法的泛型返回值(被认为是一个Object类型)作为参数传给另一个方法时,不会执行类型推断,不能编译,除非使用显示类型说明。

擦除

•ArrayList<String>.class== ArrayList<Integer>.class==ArrayList.class
•在泛型代码内部,无法获得任何有关类型参数的信息。
•泛型类型参数擦除到它的第一个边界类型。因此,在泛型类内部,只能调用边界类型定义的方法。
•使用擦除的原因是为保证迁移兼容性,即在类库实现泛型化时,客户端代码无需修改。

编译器对泛型的支持

•泛型类与非泛型类的字节码完全相同。
•在边界处,对传递进来的值进行编译期类型检查,并插入对传出去的值的转型代码(本来需要程序员写代码转型的地方)

擦除的补偿:类型实例

•在泛型类内部创建类型实例的方法
–使用类型标签Class<T>.newIntance(),但依赖于默认构造器。
–使用工厂类,为每个类型定义工厂类,由工厂方法创建类型实例。
–使用模板方法,该模板方法返回类型实例。


擦除的补偿:类型数组

•创建类型数组的方法
–使用ArrayList
–T[]array = (T[]) new Object[]
–使用Object数组,在取的时候转型
–推荐:使用类型标记
•T[] array = (T[]) Array.newInstance(type, size);

其他

•类的static方法无法访问泛型类的类型参数,所以,若要static方法需要使用泛型能力,必须使其成为泛型方法。
•多个边界时,类写在接口前面
•继承带边界的类时,本类边界必须包含父类边界

通配符?extends

•用于泛型的向上转型,如:
–List<Fruit>list 只能指向 List<Fruit>
–List<?extends Fruit> 可以等于List<Apple>


无界通配符<?>

•表明用泛型编码

•任何基本类型都不能作为类型参数

下面的代码,说明了泛型的使用方法以及场景

package test.generics;

import java.lang.reflect.Array;

public class GenericFoo<T extends Fruit> {
    private T[]      ta;
    private Class<T> clz;

    private T        x;

    public GenericFoo(T x) {
        this.x = x;

        //ERROR: Cannot instantiate the type T
        //this.x = new T(x);        
        //this.x = new T();
    }

    public GenericFoo(Class<T> clz) {
        //Cannot create a generic array of T
        //this.ta = new T[3];

        //WARNING: Type safety: Unchecked cast from Object[] to T[]
        this.ta = (T[]) new Object[3];
        
        //best way to create generic array is use Class info
        //WARNING: Type safety: Unchecked cast from Object to T[]
        this.ta = (T[]) Array.newInstance(clz, 3);
        
        
    }

    public T getX() {
        return x;
    }

    public void setX(T x) {
        this.x = x;
    }
}


package test.generics;

import java.util.ArrayList;
import java.util.List;
class Fruit {}
class Apple extends Fruit {}
class Jonathan extends Apple {}
class Orange extends Fruit {}
public class TestGenerics {
    @SuppressWarnings("unused")
    public static void main(String[] args) {
        //OK: 
        GenericFoo<Fruit> cli = new GenericFoo<Fruit>(new Fruit());

        //ERROR: Type mismatch: cannot convert from GenericFoo<Apple> to GenericFoo<Fruit>
        //GenericFoo<Fruit> cli2 = new GenericFoo<Apple>(new Apple());        

        //OK: 
        GenericFoo<? extends Fruit> cli3 = new GenericFoo<Apple>(new Apple());

        //ERROR: The method setX(capture#3-of ? extends Fruit) in the type GenericFoo<capture#3-of ? extends Fruit> is not applicable for the arguments (Apple)
        //cli3.setX(new Apple());

        //OK: 
        GenericFoo<?> cli4 = new GenericFoo<Apple>(new Apple());

        //ERROR: The method setX(capture#3-of ?) in the type GenericFoo<capture#3-of ?> is not applicable for the arguments (Apple)
        //cli4.setX(new Apple());

        //OK: 
        GenericFoo<? super Apple> cli5 = new GenericFoo<Fruit>(new Fruit());

        //ERROR: Type mismatch: cannot convert from GenericFoo<Jonathan> to GenericFoo<? super Apple>
        //GenericFoo<? super Apple> cli6 = new GenericFoo<Jonathan>(new Fruit());

        //ERROR: Bound mismatch: The type TestGenerics is not a valid substitute for the bounded parameter <T extends Fruit> of the type GenericFoo<T>
        //GenericFoo<TestGenerics> cli = new GenericFoo<TestGenerics>(new Fruit());

        //OK: 
        Number[] n = new Integer[3];
        n[0] = 1; //OK: 

        //Runtime Exception: Exception in thread "main" java.lang.ArrayStoreException: java.lang.Double
        //n[1] = 1.1;

        //OK: 
        List<Number> ln = new ArrayList<Number>();
        ln.add(1); //OK: 
        ln.add(1.1); //OK: 

        List<Integer> li = new ArrayList<Integer>();

        //ERROR: Type mismatch: cannot convert from List<Integer> to List<Number>
        //ln = li;

        //ERROR: Type mismatch: cannot convert from ArrayList<Integer> to List<Number>
        //List<Number> ln2 = new ArrayList<Integer>();

        //ERROR: Cannot create a generic array of ArrayList<String>
        //List<String>[] lsa = new ArrayList<String>[3];
    }
}




分享到:
评论

相关推荐

    net基础——泛型PPT教案学习.pptx

    net基础——泛型PPT教案学习.pptx

    C 设计新思维——泛型编程与设计范式之应用 PDF.rar

    C 设计新思维——泛型编程与设计范式之应用 PDF,候捷译序。㆒般人对C templates 的粗略印象,大约停留在「容器(containers)」的制作上。稍有研究由会发现,templates衍生出来的C Generic Programming(泛型编程)技术...

    博客《夯实JAVA基本之一——泛型详解(1)》对应源码

    在《夯实JAVA基本之一——泛型详解(1)》的博客中,作者深入浅出地探讨了泛型的基本概念和用法,本文将基于这个博客源码,详细解析泛型的相关知识点。 首先,泛型的主要目标是提高代码的类型安全性。在未引入泛型...

    博客《夯实JAVA基本之一——泛型详解(2)》对应源码

    在《夯实JAVA基本之一——泛型详解(2)》这篇博客中,作者深入探讨了泛型的高级用法和概念,这些内容对于理解和掌握Java泛型至关重要。 首先,泛型的基本语法是以尖括号 `&lt;T&gt;` 表示,其中 `T` 是一个类型参数,代表...

    C#重要知识之——泛型列表List例子

    在C#编程中,泛型列表`List&lt;T&gt;`是一个非常重要的数据结构,它为我们提供了动态数组的功能,并且具有类型安全的特性。这篇文章将深入探讨`List&lt;T&gt;`的使用,包括其基本操作、性能特点以及一些高级用法。 一、基础概念...

    细细品味C#(泛型专题)

    ### C# 泛型详解 #### 一、关于 Java、C# 泛型的看法 - **C# 与 Java 泛型的区别与优劣** 在 IT 领域,尤其是面向对象编程语言中,C# 和 Java 均提供了泛型支持来增强程序的类型安全性和复用性。尽管 C# 2.0 和 ...

    日常笔记-JAVA泛型

    日常笔记-JAVA泛型

    C++ Primer学习笔记——$11 泛型算法

    在C++编程中,泛型算法是标准库提供的强大工具,它们可以应用于各种不同类型的容器,无论容器内部存储的数据类型如何。这些算法不依赖于特定的容器实现,而是通过迭代器来操作容器中的元素,因此具有高度的通用性。...

    泛型笔记学习2009

    ### 泛型基础知识与应用详解 #### 泛型概述 泛型是Java语言的一个重要特性,它主要解决了在集合框架中频繁出现的类型转换问题,同时也增强了类型安全性。泛型的概念最早出现在Java 5.0版本中,它允许开发者创建能够...

    ASP.NET 的泛型实例

    在这个"ASP.NET的泛型实例"中,我们将深入探讨一个关键的概念——泛型。 泛型是.NET Framework 2.0引入的一项重要特性,它允许开发者在类、接口和方法中定义类型参数,从而实现数据类型的参数化。这带来了多方面的...

    SSH笔记-泛型依赖注入

    本笔记将深入探讨SSH中的Spring框架如何实现泛型依赖注入。 首先,我们来理解泛型的基本概念。泛型是Java SE 5引入的一种强大的类型系统机制,允许在类、接口和方法中使用类型参数,从而增强了代码的类型安全性和...

    Java学习笔记——良葛格

    "Java学习笔记——良葛格"是一份专为初学者设计的教程资料,由良葛格精心编写,旨在帮助读者掌握JDK5.0版本的Java基础知识。JDK(Java Development Kit)是Java开发的核心工具集,包含了编译器、调试器和运行环境等...

    本仓库记录了我的Java学习进阶之路,涵盖了Java基础、JDK源码、JVM中的重要知识,附有代码和博客讲解,旨在提供一个Java在线共享学习平台,帮助更多的Java学习入门者进阶 .zip

    作者目录Java基础Java基础学习(1)——引用Java基础学习(2)——注解Java基础学习(3)——泛型Java基础学习(4)——动态代理《Java多线程核心技术》读书笔记JDK源Java集合框架源码解读(1)——ArrayList、LinkedList和...

    清华妹子的Java仓库(进阶学习路线)

    《Java多线程核心技术》读书笔记 JDK源码 Java集合框架源码解读(1)——ArrayList、LinkedList和Vector Java集合框架源码解读(2)——HashMap Java集合框架源码解读(3)——LinkedHashMap Java集合框架源码解读(4)——...

    第14章元素增删检索——集合与泛型.ppt

    《第14章元素增删检索——集合与泛型》主要涵盖了Java编程中关于集合框架和泛型的重要概念,这是理解和高效使用Java集合类库的关键。以下是对这些知识点的详细阐述: 1. **集合框架与泛型**: - 集合框架是一套...

    C#泛型类、泛型方法、泛型接口、泛型委托的实例

    本文将深入探讨泛型类、泛型方法、泛型接口和泛型委托,并通过实例来阐述它们的应用。 首先,我们来看泛型类。泛型类是具有一个或多个类型参数的类。类型参数是在定义类时使用的占位符,实际的类型在创建类的实例时...

Global site tag (gtag.js) - Google Analytics