Unity中实现双向链表

Posted Hello Bug.

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Unity中实现双向链表相关的知识,希望对你有一定的参考价值。

一:前言

双向链表是链表的一种,和单链表一样,双链表也是由节点组成,它的每个数据结点中都有两个指针,分别指向直接后继和直接前驱。所以,从双向链表中的任意一个结点开始,都可以很方便地访问它的前驱结点和后继结点


二:代码实现

using System;
using UnityEngine;

/// <summary>
/// 双向链表
/// </summary>
public class DoubleLinkedList<T>

    private DoubleLinkedListNode<T> headNode = null;//头结点
    public DoubleLinkedListNode<T> HeadNode
    
        get  return headNode; 
    
    private DoubleLinkedListNode<T> tailNode = null;//尾结点
    public DoubleLinkedListNode<T> TailNode
    
        get  return tailNode; 
    

    protected int m_Count;//元素数量
    public int Count
    
        get  return m_Count; 
    

    /// <summary>
    /// 添加元素到头部
    /// </summary>
    public DoubleLinkedListNode<T> AddToHead(T data)
    
        if (data == null)
        
            return null;
        

        DoubleLinkedListNode<T> tempNode = new DoubleLinkedListNode<T>(data);
        if (headNode == null)
        
            headNode = tempNode;
            tailNode = tempNode;
        
        else
        
            tempNode.nextNode = headNode;
            headNode.prevNode = tempNode;
            headNode = tempNode;
        
        m_Count++;
        return headNode;
    

    /// <summary>
    /// 添加元素到尾部
    /// </summary>
    public DoubleLinkedListNode<T> AddToTail(T data)
    
        if (data == null)
        
            return null;
        

        DoubleLinkedListNode<T> tempNode = new DoubleLinkedListNode<T>(data);
        if (tailNode == null)
        
            headNode = tempNode;
            tailNode = tempNode;
        
        else
        
            tempNode.prevNode = tailNode;
            tailNode.nextNode = tempNode;
            tailNode = tempNode;
        
        m_Count++;
        return tailNode;
    

    /// <summary>
    /// 移除
    /// </summary>
    public void Remove(DoubleLinkedListNode<T> node)
    
        if (node == null)
        
            return;
        

        if (node == headNode)
        
            headNode = node.nextNode;
        
        if (node == tailNode)
        
            tailNode = node.prevNode;
        
        if (node.nextNode != null)
        
            node.nextNode.prevNode = node.prevNode;
        
        if (node.prevNode != null)
        
            node.prevNode.nextNode = node.nextNode;
        
        m_Count--;
    

    /// <summary>
    /// 从头部移除
    /// </summary>
    public void RemoveFromHead()
    
        Remove(headNode);
    

    /// <summary>
    /// 从尾部移除
    /// </summary>
    public void RemoveFromTail()
    
        Remove(tailNode);
    

    /// <summary>
    /// 把某个结点移动到头部
    /// </summary>
    public void MoveToHead(DoubleLinkedListNode<T> node)
    
        if (node == null
            || node == headNode)
        
            return;
        

        if (node == tailNode)
        
            tailNode = node.prevNode;
        
        if (node.nextNode != null)
        
            node.nextNode.prevNode = node.prevNode;
        
        if (node.prevNode != null)
        
            node.prevNode.nextNode = node.nextNode;
        
        node.prevNode = null;
        node.nextNode = headNode;
        headNode.prevNode = node;
        headNode = node;
        if (tailNode == null)
        
            tailNode = headNode;
        
    

    /// <summary>
    /// 查找某一个下标的结点
    /// </summary>
    public DoubleLinkedListNode<T> Find(int index)
    
        if (index < 0
            || index >= m_Count)
        
            throw new IndexOutOfRangeException($"索引溢出,index:index");
        

        if (index < m_Count / 2)
        
            DoubleLinkedListNode<T> tempNode = headNode;
            for (int i = 0; i < index; i++)
            
                tempNode = tempNode.nextNode;
            
            return tempNode;
        
        else
        
            DoubleLinkedListNode<T> tempNode = tailNode;
            for (int i = 0; i < m_Count - index - 1; i++)
            
                tempNode = tempNode.prevNode;
            
            return tempNode;
        
    

    /// <summary>
    /// 查找某一个结点的下标
    /// </summary>
    public int FindIndex(DoubleLinkedListNode<T> node)
    
        int index = 0;
        DoubleLinkedListNode<T> tempNode = headNode;
        if (tempNode == null)
        
            return -1;
        
        while (tempNode != null)
        
            if (tempNode == node)
            
                return index;
            
            index++;
            tempNode = tempNode.nextNode;
        
        return index;
    

    /// <summary>
    /// 是否包含某个结点
    /// </summary>
    public bool Contain(DoubleLinkedListNode<T> node)
    
        DoubleLinkedListNode<T> tempNode = headNode;
        while (tempNode != null)
        
            if (tempNode == node)
            
                return true;
            
            tempNode = tempNode.nextNode;
        
        return false;
    

    /// <summary>
    /// 清空
    /// </summary>
    public void Clear()
    
        headNode = null;
        tailNode = null;
        m_Count = 0;
    


/// <summary>
/// 双向链表结点
/// </summary>
public class DoubleLinkedListNode<T>

    public DoubleLinkedListNode<T> prevNode;//前一个结点
    public DoubleLinkedListNode<T> nextNode;//后一个结点
    public T data;//当前元素

    public DoubleLinkedListNode(T data)
    
        this.data = data;
        prevNode = null;
        nextNode = null;
    

以上是关于Unity中实现双向链表的主要内容,如果未能解决你的问题,请参考以下文章

在 C++ 中实现双向链表时面临调试问题

线性表之双向链表

[数据结构]双向链表(C语言)

LinkedList源码浅析(jdk1.8)

双向链表的建立插入删除

LRU 缓存淘汰算法