zoukankan      html  css  js  c++  java
  • 2020年9月21日 手动实现单向链表

    package com.atguigu.test03;
    
    public class SingleLinkedList {
        //这里不需要数组,不需要其他的复杂的结构,我只要记录单向链表的“头”结点
        private Node first;//first中记录的是第一个结点的地址
        private int total;//这里我记录total是为了后面处理的方便,例如:当用户获取链表有效元素的个数时,不用现数,而是直接返回total等
        
        /*
         * 内部类,因为这种Node结点的类型,在别的地方没有用,只在单向链表中,用于存储和表示它的结点关系。
         * 因为我这里涉及为内部类型。
         */
        private class Node{
            Object data;//因为数据可以是任意类型的对象,所以设计为Object
            Node next;//因为next中记录的下一个结点的地址,因此类型是结点类型
            //这里data,next没有私有化,是希望在外部类中可以不需要get/set,而是直接“结点对象.data","结点对象.next"使用
            Node(Object data, Node next){
                this.data = data;
                this.next = next;
            }
        }
        
        public void add(Object obj){
            /*
             * (1)把obj的数据,包装成一个Node类型结点对象
             * (2)把新结点“链接”当前链表的最后
             * ①当前新结点是第一个结点
             * 如何判断是否是第一个   if(first==null)说明暂时还没有第一个
             * ②先找到目前的最后一个,把新结点链接到它的next中
             * 如何判断是否是最后一个   if(某个结点.next == null)说明这个结点是最后一个
             */
    //        (1)把obj的数据,包装成一个Node类型结点对象
            //这里新结点的next赋值为null,表示新结点是最后一个结点
            Node newNode = new Node(obj, null);
            
            //①当前新结点是第一个结点
            if(first == null){
                //说明newNode是第一个
                first = newNode;
            }else{
                //②先找到目前的最后一个,把新结点链接到它的next中
                Node node = first;//创建一个新的结点,来动态表示最后一个结点;
                while(node.next != null){
                    node = node.next;
                }
                //退出循环时node指向最后一个结点
                
                //把新结点链接到它的next中
                node.next = newNode;
            }
            
            total++;
        }
        
        public int size(){
            return total;
        }
        
        public Object[] getAll(){
            //(1)创建一个数组,长度为total
            Object[] all = new Object[total];
            
            //(2)把单向链表的每一个结点中的data,拿过来放到all数组中
            Node node = first;
            for (int i = 0; i < total; i++) {
    //            all[i] = 结点.data;
                all[i] = node.data;
                //然后node指向下一个
                node = node.next;
            }
            
            //(3)返回数组
            return all;
        }
        
        public void remove(Object obj){
            if(obj == null){
                //(1)先考虑是否是第一个
                if(first!=null){//链表非空
                    
                    //要删除的结点正好是第一个结点
                    if(first.data == null){
                        //让第一个结点指向它的下一个
                        first = first.next;
                        total--;
                        return;
                    }
                    
                    //要删除的不是第一个结点
                    Node node = first.next;//第二个结点
                    Node last = first;
                    while(node.next!=null){//这里不包括最后一个,因为node.next==null,不进入循环,而node.next==null是最后一个
                        if(node.data == null){
                            last.next = node.next;
                            total--;
                            return;
                        }
                        last = node;
                        node = node.next;
                    }
                    
                    //单独判断最后一个是否是要删除的结点
                    if(node.data == null){
                        //要删除的是最后一个结点
                        last.next = null;
                        total--;
                        return;
                    }
                }
            }else{
                //(1)先考虑是否是第一个
                if(first!=null){//链表非空
                    
                    //要删除的结点正好是第一个结点
                    if(obj.equals(first.data)){
                        //让第一个结点指向它的下一个
                        first = first.next;
                        total--;
                        return;
                    }
                    
                    //要删除的不是第一个结点
                    Node node = first.next;//第二个结点
                    Node last = first;
                    while(node.next!=null){//这里不包括最后一个,因为node.next==null,不进入循环,而node.next==null是最后一个
                        if(obj.equals(node.data)){
                            last.next = node.next;
                            total--;
                            return;
                        }
                        last = node;
                        node = node.next;
                    }
                    
                    //单独判断最后一个是否是要删除的结点
                    if(obj.equals(node.data)){
                        //要删除的是最后一个结点
                        last.next = null;
                        total--;
                        return;
                    }
                }
            }
        }
    
        public int indexOf(Object obj){
            if(obj == null){
                Node node = first;
                for (int i = 0; i < total; i++) {
                    if(node.data == null){
                        return i;
                    }
                    node = node.next;
                }
            }else{
                Node node = first;
                for (int i = 0; i < total; i++) {
                    if(obj.equals(node.data)){
                        return i;
                    }
                    node = node.next;
                }
            }
            return -1;
        }
    }
    package com.atguigu.test03;
    
    import java.util.Arrays;
    
    public class TestSingleLinkedList {
    
        public static void main(String[] args) {
            SingleLinkedList list = new SingleLinkedList();
            
            list.add("张三");
            list.add("李四");
            list.add("王五");
            list.add("赵六");
            list.add("钱七");
            
            System.out.println("元素个数:" + list.size());
        
            Object[] all = list.getAll();
            System.out.println(Arrays.toString(all));
            
            /*list.remove("张三");
            System.out.println("元素个数:" + list.size());
            all = list.getAll();
            System.out.println(Arrays.toString(all));
            
            list.remove("王五");
            System.out.println("元素个数:" + list.size());
            all = list.getAll();
            System.out.println(Arrays.toString(all));
            
            list.remove("钱七");
            System.out.println("元素个数:" + list.size());
            all = list.getAll();
            System.out.println(Arrays.toString(all));*/
            
            System.out.println(list.indexOf("张三"));
            System.out.println(list.indexOf("王五"));
            System.out.println(list.indexOf("钱七"));
        }
    
    }
  • 相关阅读:
    Java中Date日期字符串格式的各种转换
    Redis集群搭建与简单使用
    Java中的Redis应用
    java的linux命令
    Lucene全文检索引擎
    设置Xshell中支持中文
    Java并发Fork-Join框架原理解析
    java线程
    Django-路由层
    Django简介
  • 原文地址:https://www.cnblogs.com/douyunpeng/p/13705687.html
Copyright © 2011-2022 走看看