自定义LinkedList

LinkedList是通过双向链表实现的。

下面实现LinkedList类的以下方法:

  1. clear():清空整个链表
  2. size():获取链表的大小
  3. isEmpty():判断链表是否为空
  4. get(int index):获取链表在某个索引处的节点中的数据
  5. set(int index,Object data):设置链表中在index索引处的节点中的数据,并返回该索引之前的节点中的数据
  6. add(Object data):往链表中添加节点元素(其实新添加的节点都是尾节点,尾插法)
  7. remove(int index):删除链表中该索引出的节点,并返回该索引之前的节点中的数据
  8. 实现LinkedList的迭代器(Iterator),实现hasnext()、next()、remove()方法,这里remove()方法必须在调用了next()方法之后才能调用
package com.test.test;

import java.util.Iterator;
import java.util.NoSuchElementException;

public class Test3 {

    public static void main(String[] args) {
        MyLinkedList<String> mList = new MyLinkedList<String>();
        mList.add("纯");
        mList.add("牛");
        mList.add("奶");

        System.out.println(mList.isEmpty());
        System.out.println(mList.size());

        mList.set(1, "酸");

        for (int i = 0; i < mList.size(); i++) {
            String data = mList.get(i);
            System.out.println(data);
        }

        Iterator iterator = mList.iterator();
        while(iterator.hasNext()){
            String data = (String) iterator.next();
            iterator.remove();
            System.out.println(data);
        }
        System.out.println(mList.size());

        mList.clear();
        System.out.println(mList.isEmpty());
        System.out.println(mList.size());

    }

}

/**
 * 自定义的LinkedList类 2015年10月20日 下午8:57:58
 * 
 * @author 张耀晖
 *
 * @param <Object>
 */
class MyLinkedList<Object> implements Iterable<Object> {

    private int theSize;// 链表的大小
    private Node<Object> beginMarker;// 头节点
    private Node<Object> endMarker;// 尾节点

    public MyLinkedList() {
        clear();
    }

    // 清空链表
    public void clear() {
        beginMarker = new Node(null, null, null);// 初始化头节点
        endMarker = new Node(null, beginMarker, null);// 初始化尾节点
        beginMarker.next = endMarker;// 设置头节点的后继节点为尾节点

        theSize = 0;// 链表大小设为0
    }

    // 获取链表的大小
    public int size() {
        return theSize;
    }

    // 判断链表是否为空
    public boolean isEmpty() {
        return size() == 0;
    }

    // 获取链表中index位置处的数据
    public Object get(int index) {
        return getNode(index).data;
    }

    // 修改链表中index位置处的节点的数据,返回该位置原先的节点的数据
    public Object set(int index, Object data) {
        Node<Object> indexNode = getNode(index);// 得到该位置的原先的节点
        Object indexData = indexNode.data;// 得到该位置原先节点的数据
        indexNode.data = data;// 修改该位置出的节点的数据

        return indexData;
    }

    // 向链表中的最后的位置添加数据
    public boolean add(Object data) {
        add(size(), data);
        return true;
    }

    // 向链表的index位置添加数据data
    public void add(int index, Object data) {
        Node<Object> indexNode = getNode(index);// 得到该位置的原先的节点
        Node<Object> newNode = new Node(data, indexNode.prior, indexNode);// 构造新的节点,并设置该节点的前驱节点为原先节点的前驱节点,后继节点为原先的节点
        newNode.prior.next = newNode;// 修改原先节点的后继节点为新节点
        indexNode.prior = newNode;// 原先节点的前驱节点为新节点

        theSize++;// 链表大小加1
    }

    // 删除链表index位置处的数据,返回删除位置节点的数据
    public Object remove(int index) {
        Node<Object> indexNode = getNode(index);// 得到该位置的原先的节点
        remove(indexNode);
        return indexNode.data;
    }

    // 删除链表中的该节点
    private void remove(Node<Object> indexNode) {
        indexNode.prior.next = indexNode.next;// 设置原先节点的前驱节点的后继节点为原先节点的后继节点
        indexNode.next.prior = indexNode.prior;// 设置原先节点的后继节点的前驱节点为原先节点的前驱节点

        theSize--;// 链表的大小减1
    }

    // 返回给定位置处的节点元素
    private Node<Object> getNode(int index) {

        Node<Object> indexNode = null;

        if (index < 0 || index > size()) { // 判断输入的index索引是否合法
            throw new IndexOutOfBoundsException();
        }
        if (index < size() / 2) {// 判断index在整个链表的前半部分
            indexNode = beginMarker.next;// 假设indexNode为链表的第一个节点
            for (int i = 0; i < index; i++) {// 依次根据next找到index索引处的节点
                indexNode = indexNode.next;
            }
        } else {// 判断index在整个链表的后半部分
            indexNode = endMarker;// 假设indexNode为链表的尾节点
            for (int i = size(); i > index; i--) {// 依次根据prior找到index索引出的节点
                indexNode = indexNode.prior;
            }
        }

        return indexNode;
    }

    @Override
    public Iterator<Object> iterator() {
        return new LinkedListIterator();
    }

    private class LinkedListIterator implements Iterator<Object> {

        private Node<Object> current = beginMarker.next;// 初始化current为链表的第一个节点
        private boolean okToRemove = false;// 是否可以使用remove()方法的标志

        @Override
        // 判断是否存在下一个节点
        public boolean hasNext() {
            return current != endMarker;// 只要current不是尾节点,说明current之后还存在下一个节点
        }

        @Override
        // 返回下一个节点中的数据
        public Object next() {

            if (!hasNext()) {
                throw new NoSuchElementException();
            }
            Object data = current.data;
            current = current.next;

            okToRemove = true;
            return data;
        }

        @Override
        // 删除节点
        public void remove() {
            if (!okToRemove) {// 作用是使得remove方法只能在next()使用之后调用
                throw new IllegalStateException();
            }

            MyLinkedList.this.remove(current.prior);// 删除当前节点的前驱节点,也就是刚才通过next()返回的节点
            okToRemove = false;
        }

    }

    /*
     * Node(节点类)
     */
    private class Node<Object> {
        public Object data;
        public Node<Object> prior;
        public Node<Object> next;

        public Node(Object data, Node<Object> prior, Node<Object> next) {
            this.data = data;
            this.prior = prior;
            this.next = next;
        }
    }

}

打印结果:
这里写图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
要将List<Object>转换为LinkedList<自定义类>,可以按照以下步骤进行操作: 1. 创建一个空的LinkedList<自定义类>对象。 2. 遍历List<Object>中的每个元素。 3. 将每个元素强制转换为自定义类,并将其添加到LinkedList<自定义类>中。 4. 重复步骤2和步骤3,直到遍历完List<Object>中的所有元素。 5. 返回转换后的LinkedList<自定义类>对象。 下面是一个示例代码: ```java List<Object> list = new ArrayList<>(); // 假设list中已经包含了自定义类的对象 LinkedList<自定义类> linkedList = new LinkedList<>(); for (Object obj : list) { 自定义类 customObj = (自定义类) obj; linkedList.add(customObj); } // 现在linkedList就是List<Object>转换后的LinkedList<自定义类>对象 ``` 请注意,这个示例假设List<Object>中的每个元素都是自定义类的对象,并且已经进行了正确的强制转换。如果List<Object>中的元素不是自定义类的对象,或者无法进行强制转换,将会抛出ClassCastException异常。你需要根据实际情况进行检查和处理。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* *2* *3* [Java-自定义LinkedList类](https://blog.csdn.net/qq_52998673/article/details/126282673)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_1"}}] [.reference_item style="max-width: 100%"] [ .reference_list ]

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值