Java泛型数组

本文探讨了在Java中使用链表和可变数组实现数据结构如队列和栈时遇到的问题。对于可变数组,作者介绍了动态扩容的策略:数组满时容量翻倍,元素不足容量1/4时容量减半。然而,Java中初始化泛型数组存在挑战,作者通过创建Object[]数组并强制转换为T[]来解决,尽管这种方法并不理想。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

  • 最近使用Java实现队列、栈这些基本的数据结构时,我分别采用了LinkedList列表和ResizeArray可变数来实现,先看看基本的API:
/*
 * 栈API: 抽象出基本的栈的操作
 */
public interface Stack<T> {
    /*
     * 出栈
     */
    public T pop();
    /*
     * 进栈
     */
    public void push(T item);
    /*
     * 判断栈是否为空
     */
    public boolean isEmpty();
}
  • 使用链表结构实现栈数据结构:
/*
 * 使用链表实现Stack
 */
public class StackLinkedList<T> implements Stack<T>{
    /*
     * 栈顶元素
     */
    private Node<T> first = null; //栈顶元素初始化为null
    /*
     * 私有类实现节点对象
     */
    @SuppressWarnings("hiding")
    private class Node<T>{
        T item;
        Node<T> next;
    }
    @Override
    public T pop() {
        T item = first.item; 
        first = first.next;
        return item;
    }

    @Override
    public void push(T item) {
        Node<T> oldfirst = first;
        first = new Node<T>();
        first.item = item;
        first.next = oldfirst;      
    }

    @Override
    public boolean isEmpty() {
        return first==null;
    }

}
  • 使用可变数组时出现了一些问题,首先需要考虑的是使用数组时扩容的问题,我分别采取的是:
    • 当数组满了时,将数组容量扩大一倍;
    • 当数组元素不足数组容量的1/4时将数组容量缩小一半
  • 另一个问题是无法初始化泛型数组,采取的方式是先创建一个Object[]数组,然后将其强制类型转换为T[],但实际上这种强制类型转换是很不友好的,但我不得不这么做(⊙o⊙)…
public class StackResizeArray<T> implements Stack<T>{

    /*
     * 使用数组存储栈中元素
     */
    private T[] array;

    /*
     * 栈顶元素的下一个位置
     */
    private int n;

    /*
     * 构造函数初始化数组容量为1
     */
    @SuppressWarnings("unchecked")
    public StackResizeArray(){
        array = (T[])new Object[1];  //数组不能直接初始化为泛型数组,必须像这样先申明为Object再强制类型转换
        n = 0;
    }

    /*
     * 改变数组容量
     */
    @SuppressWarnings("unchecked")
    private void resize(int capacity) {
        T[] newarray = (T[])new Object[capacity];
        for(int i=0; i<n; i++){
            newarray[i] = array[i];
        }
        array = newarray;
    }
    /*
     * 出栈: 当数组元素不足1/4时将数组大小缩小一半
     */
    @Override
    public T pop() {
        T item = array[--n];
        array[n] = null;  //手动释放出栈元素,便于垃圾回收
        if(n>0 && n<array.length/4){ 
            resize(array.length/2);
        }
        return item;
    }
    /*
     * 入栈: 当数组满时将数组容量扩大一倍
     */
    @Override
    public void push(T item) {
        if(n==array.length){
            resize(array.length*2);
        }
        array[n++] = item;
    }

    @Override
    public boolean isEmpty() {
        return n==0;
    }

}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值