泛型和枚举的学习笔记

泛型Generic

泛型类

package demo;

public class SuperArray<T> {
    private Object[] array;
    //根据下标查询数字

    //当前最后一个数字的下边,要为-1 ,以为数组的第一个下标为0
    private int currentIndex = -1;

    //构造是初始化
    public SuperArray(){
        array = new Object[8];
    }

    //添加数据的方法
    public void add(T data){
        System.out.println("我是数组的实现!---add");
        currentIndex++;
        //自动扩容
        if(currentIndex > array.length-1){
            array = dilatation(array);
        }
        array[currentIndex] = data;
    }

    public T get(int index){
        System.out.println("我是数组的实现---get");
        return (T)array[index];
    }

    //数组扩容的方法
    private Object[] dilatation(Object[] oldArray){
        Object[] newArray = new Object[oldArray.length * 2];
        for (int i = 0; i < oldArray.length; i++) {
            newArray[i] = oldArray[i];
        }
        return newArray;
    }

    //验证下标是否合法
    private boolean validateIndex(int index) {
        //只要有一个不满足就返回false
        return index <= currentIndex && index >= 0;
    }

    public static void main(String[] args) {
        SuperArray<String> superArray=new SuperArray<>();
        superArray.add("123");
        superArray.add("456");
        System.out.println(superArray.get(1));
    }
}

在类后加入,使用时声明该泛型是哪个类

泛型方法

package demo;

public class Demo1 {
    public <T> T show(T t){
        System.out.println(t);
        return t;
    }

    public static <T> T show2(T t){
        System.out.println(t);
        return t;
    }

    public static void main(String[] args) {
        Demo1 demo1 = new Demo1();
        Integer show = demo1.show(123);
        String s = Demo1.show2("123");

    }
}

方法定义要加入, 最后尽量返回泛型,如果不返回的话,相当于用Object

泛型继承

public interface Comparator<T>{
    int compare(T t1,T t2);
}
package demo;

public class User {
    private String name;
    private Integer age;

    public User() {
    }

    public User(String name, Integer age) {
        this.name = name;
        this.age = age;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Integer getAge() {
        return age;
    }

    public void setAge(Integer age) {
        this.age = age;
    }
}

package demo;

public class UserComparator implements Comparator<User>{

    @Override
    public int compare(User t1, User t2) {
        return t1.getAge()- t2.getAge();
    }
}

package demo;

public class Test1 {
    public static void main(String[] args) {
        UserComparator userComparator=new UserComparator();
//        Comparator<User> userComparator=new UserComparator();
        int compare = userComparator.compare(new User("zs", 18), new User("ls", 16));
        System.out.println(compare);
    }
}

明确类型的泛型继承,也可以用不明确类型的,(把UserComparator替换成泛型类)

类型通配符

  • 无界(SuperArray<?> superArray)
  • 上界((SuperArray<? extends Dog> superArray) dog类及其子类都能放入数组
  • 下界 (SuperArray<? super Dog> superArray) dog类及其父类都能放入数组

类型擦除

  • 不能用类型参数替换基本类型。就比如,没有SuperArray<double>,只有SuperArray<Double>。因为当类型擦除后,SuperArray的原始类型变为Object,但是Object类型不能存储double值,只能引用Double的值

  • 泛型被擦除后,其实这两个方法是一致的,并不能构成泛型。

    image

  • 类型擦除和多态冲突 虚拟机巧妙的使用了桥方法,来解决了类型擦除和多态的冲突(类型擦除后,JVM自动补充方法把Object方法补充,区分Date的方法,来区分方法调用)

静态方法和静态类中的问题

public class Test2<T> {    
    public static T one;   //编译错误    
    public static T show(T one){ //编译错误    
        return null;    
    }    
}

因为泛型类中的泛型参数的实例化是在定义对象的时候指定的,而静态变量和静态方法不需要使用对象来调用。对象都没有创建,如何确定这个泛型参数是何种类型,所以当然是错误的。

public class Test2<T> {    

    public static <T> T show(T one){ //这是正确的    
        return null;    
    }    
}

因为这是泛型方法

枚举 enum

枚举基本特性

本质是静态常量

public class SeasonConstant {
    public static final int SPRING = 1;
    public static final int SUMMER = 2;
    public static final int AUTUMN = 3;
    public static final int WINTER = 4;
}
public enum SeasonEnum {
    SPRING,SUMMER,AUTUMN,WINTER;
}
values() 静态的自动生成的可以遍历enum实例,其返回enum实例的数组
ordinal() 父类的实例方法返回每个实例在声明时的次序
name() 父类的实例方法返回enum实例声明时的名称
getDeclaringClass()返回其所属的enum类
valueOf() 静态的自动生成的根据给定的名称返回相应的enum实例
package demo;

public class Test1 {
    public static void main(String[] args) {
        SeasonEnum[] values = SeasonEnum.values();
        for (int i = 0; i < values.length; i++) {
            System.out.println(values[i].name());
            System.out.println(values[i].ordinal());
            System.out.println(values[i].getDeclaringClass());
            System.out.println("----------------");
        }
    }
}

Enum中添加新方法

public enum SeasonEnum {
    SPRING("春天","春暖花开的季节"),
    SUMMER("夏天","热的要命,但是小姐姐都穿短裤"),
    AUTUMN("秋天","果实成熟的季节"),
    WINTER("冬天","冷啊,可以吃火锅");

    private String name;
    private String detail;

    SeasonEnum() {
    }

    SeasonEnum(String name, String detail) {
        this.name = name;
        this.detail = detail;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getDetail() {
        return detail;
    }

    public void setDetail(String detail) {
        this.detail = detail;
    }
}

Switch语句中的Enum

public static void main(String[] args) {
    SeasonEnum season = SeasonEnum.SPRING;
    switch (season){
        case SPRING:
            System.out.println("春天来了,又到了万物交配的季节!");
        case SUMMER:
            System.out.println("夏天来了,又可以穿大裤衩了!");
        case AUTUMN:
            System.out.println("秋天来了,又到了收获的季节!");
        case WINTER:
            System.out.println("冬天来了,又到了吃火锅的季节了!");
        default:
            System.out.println("也没有别的季节了。");
    }
}
  • 常规情况下必须使用 enum 类型来修饰 enum 实例,但在 case 语句中不必如此,
  • 意思就是 case SPRING: 不需要写成 case SeasonEnum.SPRING:

枚举的优势

阿里《Java开发手册》对枚举的相关规定如下:

【强制】所有的枚举类型字段必须要有注释,说明每个数据项的用途。

【参考】枚举类名带上 Enum 后缀,枚举成员名称需要全大写,单词间用下划线隔开。说明:枚举其实就是特殊的常量类,且构造方法被默认强制是私有。正例:枚举名字为 ProcessStatusEnum 的成员名称:SUCCESS / UNKNOWN_REASON。

  • int 类型本身并不具备安全性,假如某个程序员在定义 int 时少些了一个 final 关键字,那么就会存在被其他人修改的风险,而反观枚举类,它“天然”就是一个常量类,不存在被修改的风险
  • 使用 int 类型的语义不够明确,比如我们在控制台打印时如果只输出 1…2…3 这样的数字,我们肯定不知道它代表的是什么含义
  • 对程序修改常量时,只需要对枚举修改,不用对所有常量进行修改
  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值