表达式2叉树(前序,中序,后序)的非递归实现_模板实现

测试程序

/// @file exam_x_x.cpp
/// @brief exam_2
/**
* 编写表达式2叉树(前序,中序,后序)的非递归实现
提示 : 用栈实现, 模拟的方法: 先用递归实现, 单步跟一遍, 看栈上数据的变化, 再用栈模拟.
*/

#include <iostream>
#include <limits>

#include "MyTree.h"

using namespace std;

void clear_cin();
void fnTestTree();

int main(int argc, char** argv, char** envp)
{
    fnTestTree();

    /**
    tree.printTree_DLR:
    - + A / * B - C D - E F G
    tree.printTree_DLR_ex:
    - + A / * B - C D - E F G
    tree.printTree_LDR:
    A + B * C - D / E - F - G
    tree.printTree_LDR_ex:
    A + B * C - D / E - F - G
    tree.printTree_LRD:
    A B C D - * E F - / + G -
    tree.printTree_LRD_ex:
    A B C D - * E F - / + G -
    */

    cout << "END, press any key to quit" << endl;
    clear_cin();
    getchar();

    return 0;
}

void fnTestTree()
{
    //----------------------------------------------------------------------
    // 建立树 
    //----------------------------------------------------------------------
    // A + B*(C-D)/(E-F) - G
    CMyTree<char> tree;
    CMyTreeNode<char>* pRootNode = NULL;
    CMyTreeNode<char>* pNodeCur = NULL;
    CMyTreeNode<char>* pNodeTmp1 = NULL;
    CMyTreeNode<char>* pNodeTmp2 = NULL;
    CMyTreeNode<char>* pNodeTmp3 = NULL;
    CMyTreeNode<char>* pNodeTmp4 = NULL;
    CMyTreeNode<char>* pNodeTmp5 = NULL;

    // C-D
    pNodeTmp1 = tree.MakeNewNode('-');
    tree.insertNode(pNodeTmp1, NODE_LEFT, 'C');
    tree.insertNode(pNodeTmp1, NODE_RIGHT, 'D');

    // E-F 
    pNodeTmp2 = tree.MakeNewNode('-');
    tree.insertNode(pNodeTmp2, NODE_LEFT, 'E');
    tree.insertNode(pNodeTmp2, NODE_RIGHT, 'F');

    // B*(C-D)
    pNodeTmp3 = tree.MakeNewNode('*');
    tree.insertNode(pNodeTmp3, NODE_LEFT, 'B');
    tree.insertNode(pNodeTmp3, NODE_RIGHT, pNodeTmp1);

    // B*(C-D)/(E-F)
    pNodeTmp4 = tree.MakeNewNode('/');
    tree.insertNode(pNodeTmp4, NODE_LEFT, pNodeTmp3);
    tree.insertNode(pNodeTmp4, NODE_RIGHT, pNodeTmp2);

    // A + B*(C-D)/(E-F)
    pNodeTmp5 = tree.MakeNewNode('+');
    tree.insertNode(pNodeTmp5, NODE_LEFT, 'A');
    tree.insertNode(pNodeTmp5, NODE_RIGHT, pNodeTmp4);

    // A + B*(C-D)/(E-F) - G
    pRootNode = tree.insertRootNode('-');
    tree.insertNode(pRootNode, NODE_LEFT, pNodeTmp5);
    tree.insertNode(pRootNode, NODE_RIGHT, 'G');

    //----------------------------------------------------------------------
    // 遍历树 - 前序打印 ok
    //----------------------------------------------------------------------
    // - + A / * B - C D - E F G
    printf("tree.printTree_DLR:\n");
    tree.printTree_DLR(tree.getRootNode()); ///< 递归实现
    printf("\n");

    printf("tree.printTree_DLR_ex:\n");
    tree.printTree_DLR_ex(tree.getRootNode()); ///< 非递归实现
    printf("\n");

    //----------------------------------------------------------------------
    // 遍历树 - 中序打印 
    //----------------------------------------------------------------------
    // A + B * C - D / E - F - G
    printf("tree.printTree_LDR:\n");
    tree.printTree_LDR(tree.getRootNode()); ///< 递归实现
    printf("\n");

    printf("tree.printTree_LDR_ex:\n");
    tree.printTree_LDR_ex(tree.getRootNode()); ///< 非递归实现
    printf("\n");

    //----------------------------------------------------------------------
    // 遍历树 - 逆序打印 ok
    //----------------------------------------------------------------------
    // A B C D - * E F - / + G -
    printf("tree.printTree_LRD:\n");
    tree.printTree_LRD(tree.getRootNode()); ///< 递归实现
    printf("\n");

    printf("tree.printTree_LRD_ex:\n");
    tree.printTree_LRD_ex(tree.getRootNode()); ///< 非递归实现
    printf("\n");

    // A + B*(C-D)/(E-F) - G
    // 后序遍历表达式的模拟计算
    // A B C D - * E F - / + G -
    // A B (C-D) * E F - / + G -
    // A B*(C-D) E F - / + G -
    // A B*(C-D) (E-F) / + G -
    // A B*(C-D)/(E-F) + G -
    // A+B*(C-D)/(E-F) G -
    // A+B*(C-D)/(E-F)-G
}   

void clear_cin()
{
    cin.clear();
    cin.sync();
}

模板实现

// MyTree.h: interface for the CMyTree class.
//
//

#if !defined(AFX_MYTREE_H__4898D3E6_65B2_4A17_9CA5_910BEF38E313__INCLUDED_)
#define AFX_MYTREE_H__4898D3E6_65B2_4A17_9CA5_910BEF38E313__INCLUDED_

#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000

#define NODE_LEFT true
#define NODE_RIGHT false

#include <assert.h>
#include "LsStack.h"

template<typename T>
class CMyTreeNode
{
public:
    CMyTreeNode()
        : m_Element((T)0)
        , m_pParent(NULL)
        , m_pChildLeft(NULL)
        , m_pChildRight(NULL)
    {}

    ~CMyTreeNode() {}

    T m_Element; ///< 元素
    CMyTreeNode* m_pParent; ///< 父节点
    CMyTreeNode* m_pChildLeft; ///< 左孩子结点
    CMyTreeNode* m_pChildRight; ///< 右孩子结点
};

template<typename T>
class CMyTree  
{
public:
    CMyTree() : m_pRoot(NULL) {}
    virtual ~CMyTree() {free(m_pRoot);}

    CMyTreeNode<T>* insertRootNode(T Element);
    CMyTreeNode<T>* MakeNewNode(T Element);
    CMyTreeNode<T>* insertNode(CMyTreeNode<T>* pNode, bool isLeft, T Element);
    CMyTreeNode<T>* insertNode(CMyTreeNode<T>* pNode, bool isLeft, CMyTreeNode<T>* pNodeChildExist);

    CMyTreeNode<T>* getRootNode() {return m_pRoot;}

    /// 用递归实现遍历
    void printTree_DLR(CMyTreeNode<T>* pTreeNode); ///< 前序-遍历打印
    void printTree_LDR(CMyTreeNode<T>* pTreeNode); ///< 中序-遍历打印
    void printTree_LRD(CMyTreeNode<T>* pTreeNode); ///< 后序-遍历打印

    /// 用非递归实现遍历
    void printTree_DLR_ex(CMyTreeNode<T>* pTreeNode); ///< 前序-遍历打印
    void printTree_LDR_ex(CMyTreeNode<T>* pTreeNode); ///< 中序-遍历打印
    void printTree_LRD_ex(CMyTreeNode<T>* pTreeNode); ///< 后序-遍历打印

    void free(CMyTreeNode<T>* pTreeNode); ///< 释放资源
private:
    CMyTreeNode<T>* m_pRoot;
};

template<typename T>
void CMyTree<T>::free(CMyTreeNode<T>* pTreeNode)
{
    /// 按照LRD后序释放资源合理
    if (NULL != pTreeNode)
    {
        if (NULL != pTreeNode->m_pChildLeft)
            free(pTreeNode->m_pChildLeft);
        
        if (NULL != pTreeNode->m_pChildRight)
            free(pTreeNode->m_pChildRight);
        
        if (NULL != pTreeNode->m_pParent)
            pTreeNode->m_pParent = NULL;

        delete pTreeNode;
        pTreeNode = NULL;
    }
}

template<typename T>
void CMyTree<T>::printTree_DLR(CMyTreeNode<T>* pTreeNode)
{
    if (NULL != pTreeNode)
    {
        cout << pTreeNode->m_Element << " ";
        printTree_DLR(pTreeNode->m_pChildLeft);
        printTree_DLR(pTreeNode->m_pChildRight);
    }
}

template<typename T>
void CMyTree<T>::printTree_LDR(CMyTreeNode<T>* pTreeNode)
{
    if (NULL != pTreeNode)
    {
        if (NULL != pTreeNode->m_pChildLeft)
            printTree_LDR(pTreeNode->m_pChildLeft);

        cout << pTreeNode->m_Element << " ";

        if (NULL != pTreeNode->m_pChildRight)
            printTree_LDR(pTreeNode->m_pChildRight);
    }
}

template<typename T>
void CMyTree<T>::printTree_LRD(CMyTreeNode<T>* pTreeNode)
{
    if (NULL != pTreeNode)
    {
        if (NULL != pTreeNode->m_pChildLeft)
            printTree_LRD(pTreeNode->m_pChildLeft);

        if (NULL != pTreeNode->m_pChildRight)
            printTree_LRD(pTreeNode->m_pChildRight);
        
        cout << pTreeNode->m_Element << " ";
    }
}

template<typename T>
void CMyTree<T>::printTree_DLR_ex(CMyTreeNode<T>* pTreeNode)
{
    CMyTreeNode<T>* pTreeNodeTmp = NULL;
    CLsStack<CMyTreeNode<T>*> stack;
    CLsStack<T> stack2;
    CLsStack<T> stack3;
    
    if (NULL != pTreeNode)
    {
        /// 空指针不能向栈中压, 影响逻辑判断
        if (NULL != pTreeNode)
            stack.push(pTreeNode);
        
        pTreeNodeTmp = pTreeNode;
        while (NULL != pTreeNodeTmp)
        {
            if (stack.isEmpty())
                break;
            
            pTreeNodeTmp = stack.pop();
            if (NULL != pTreeNodeTmp)
            {
                stack2.push(pTreeNodeTmp->m_Element);
            }
            
            if (NULL != pTreeNodeTmp)
            {
                if (NULL != pTreeNodeTmp->m_pChildRight)
                    stack.push(pTreeNodeTmp->m_pChildRight);

                if (NULL != pTreeNodeTmp->m_pChildLeft)
                    stack.push(pTreeNodeTmp->m_pChildLeft);
            }
        }
    }
    
    /// 发现和前序正好是相反的, 掉个方向
    while (!stack2.isEmpty())
    {
        stack3.push(stack2.pop());
    }

    while (!stack3.isEmpty())
    {
        cout << stack3.pop() << " ";
    }
}

template<typename T>
void CMyTree<T>::printTree_LDR_ex(CMyTreeNode<T>* pTreeNode)
{
    CMyTreeNode<T>* pTreeNodeTmp = NULL;
    CLsStack<CMyTreeNode<T>*> stack;
    CLsStack<T> stack2;
    CLsStack<T> stack3;
    
    if (NULL != pTreeNode)
    {
        /// 空指针不能向栈中压, 影响逻辑判断
        pTreeNodeTmp = pTreeNode;
        while ((NULL != pTreeNodeTmp) || !stack.isEmpty())
        {
            if (NULL != pTreeNodeTmp)
            {
                stack.push(pTreeNodeTmp);
                pTreeNodeTmp = pTreeNodeTmp->m_pChildLeft;
            }
            else
            {
                pTreeNodeTmp = stack.pop();
                stack2.push(pTreeNodeTmp->m_Element);
                pTreeNodeTmp = pTreeNodeTmp->m_pChildRight;
            }
        }
    }
    
    /// 发现和中序正好是相反的, 掉个方向
    while (!stack2.isEmpty())
    {
        stack3.push(stack2.pop());
    }
    
    while (!stack3.isEmpty())
    {
        cout << stack3.pop() << " ";
    }
}

template<typename T>
void CMyTree<T>::printTree_LRD_ex(CMyTreeNode<T>* pTreeNode)
{
    CMyTreeNode<T>* pTreeNodeTmp = NULL;
    CLsStack<CMyTreeNode<T>*> stack;
    CLsStack<CMyTreeNode<T>*> stack2;

    if (NULL != pTreeNode)
    {
        /// 空指针不能向栈中压, 影响逻辑判断
        if (NULL != pTreeNode)
            stack.push(pTreeNode);

        pTreeNodeTmp = pTreeNode;
        while (NULL != pTreeNodeTmp)
        {
            if (stack.isEmpty())
                break;

            pTreeNodeTmp = stack.pop();

            if (NULL != pTreeNodeTmp)
            {
                stack2.push(pTreeNodeTmp);
            }
            else
            {
                assert(0);
            }

            if (NULL != pTreeNodeTmp)
            {
                /// 必须先压左孩子, 再压入右孩子, 才会逆序遍历
                if (NULL != pTreeNodeTmp->m_pChildLeft)
                    stack.push(pTreeNodeTmp->m_pChildLeft);

                if (NULL != pTreeNodeTmp->m_pChildRight)
                    stack.push(pTreeNodeTmp->m_pChildRight);
            }
        }
    }

    while (!stack2.isEmpty())
    {
        pTreeNodeTmp = stack2.pop();

        if (NULL != pTreeNodeTmp)
            cout << pTreeNodeTmp->m_Element << " ";
    }
}

template<typename T>
CMyTreeNode<T>* CMyTree<T>::insertRootNode(T Element)
{
    if (NULL == m_pRoot)
    {
        m_pRoot = new CMyTreeNode<T>;
        m_pRoot->m_Element = Element;
    }

    return m_pRoot;
}

template<typename T>
CMyTreeNode<T>* CMyTree<T>::MakeNewNode(T Element)
{
    CMyTreeNode<T>* pNewNode = new CMyTreeNode<T>;
    pNewNode->m_Element = Element;
    
    return pNewNode;
}

template<typename T>
CMyTreeNode<T>* CMyTree<T>::insertNode(CMyTreeNode<T>* pNode, bool isLeft, T Element)
{
    CMyTreeNode<T>* pNodeChild = NULL;
    if (NULL != pNode)
    {
        pNodeChild = new CMyTreeNode<T>;
        pNodeChild->m_Element = Element;
        pNodeChild->m_pParent = pNode;

        if (isLeft)
            pNode->m_pChildLeft = pNodeChild;
        else
            pNode->m_pChildRight = pNodeChild;
    }
    
    return pNode;
}

template<typename T>
CMyTreeNode<T>* CMyTree<T>::insertNode(CMyTreeNode<T>* pNode, bool isLeft, CMyTreeNode<T>* pNodeChildExist)
{
    if (NULL != pNode)
    {
        if (NULL != pNodeChildExist)
            pNodeChildExist->m_pParent = pNode;

        if (isLeft)
            pNode->m_pChildLeft = pNodeChildExist;
        else
            pNode->m_pChildRight = pNodeChildExist;
    }
    
    return pNodeChildExist;
}

#endif // !defined(AFX_MYTREE_H__4898D3E6_65B2_4A17_9CA5_910BEF38E313__INCLUDED_)

// LsStack.h: interface for the CLsLinkedList class.
//
//

#if !defined(LSSTACK_H_82FEA8FE_F7B8_4CD7_A162_751580726632)
#define LSSTACK_H_82FEA8FE_F7B8_4CD7_A162_751580726632

#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000

#include "LsDoublyLinkedList.h"

/**
栈
    栈也是线性表.
    栈是先进后出, 只操作栈顶的数据结构.
    栈是可以回溯的
    栈可以用来计算用来制作堆栈机, 用堆栈机算法来模拟逆波兰表达式的运算结果, 可以模拟汇编指令的执行, 用于虚拟机.
实现方法
    * 用链表类实现
    继承于链表, 只在头部操作(增加,删除).
    * 用数组类实现
    继承于数组, 只在尾部操作(增加,删除).
*/
template<typename T>
class CLsStack : public CLsLinkedList<T>
{
public:
    CLsStack()
    {
    }

    virtual ~CLsStack()
    {
    }

    void push(T Element);
    T pop();
};

template<typename T>
void CLsStack<T>::push(T Element)
{
    addHead(Element);
}

template<typename T>
T CLsStack<T>::pop()
{
    T Rc = (T)0;

    if (getLength() > 0)
    {
        Rc = *getHead();
        removeHead();
    }

    return Rc;
}

#endif // !defined(LSSTACK_H_82FEA8FE_F7B8_4CD7_A162_751580726632)

// LsDoublyLinkedList.h: interface for the CLsLinkedList class.
//
//

#if !defined(LSDOUBLYLINKEDLIST_H_82FEA8FE_F7B8_4CD7_A162_751580726632)
#define LSDOUBLYLINKEDLIST_H_82FEA8FE_F7B8_4CD7_A162_751580726632

/**
链表总结
空间
    链式存储
时间复杂度
    尽量避免提供非常量阶的接口
    增加操作: O(1) 常量阶, 快
    删除操作: O(1) 常量阶, 快
    修改操作:O(1) 快(条件:知道位置, 用的是先前返回的位置类或结点指针)
    查询操作:O(n) 线性阶, 慢
    随机访问:O(n) 线性阶, 慢
使用场合
    * 问题规模不确定
    * 随机访问频率低
    * 数据更新频率高(主要指的是添加和删除操作)
缺点
    * 查询速度慢(数组和链表查询速度都慢)
原生new的时间复杂度
    new实现是线性阶.
    调用的memset是线性阶, 有循环操作.
    HeapAlloc中没源码, 但是有循环操作, 是线性阶.
    new不影响时间增长率.

结论
    当算法中, new次数较少时, 可以忽略new对算法时间复杂度的影响.
    当new次数较多时, 可以一次多new几个元素(e.g. 10个), 下次就不用new, 直接取已经new好的数据操作, 等用完了, 才再次new几个元素出来.
    这样对new操作做优化, 等于自己做堆管理, 需要再做一个链表, 将new出来的10个一组的小块内存空间管理起来, 当一个类指针不用了, 就称为闲置空间, 放在内存池中. 下次不用再申请了, 可以复用.
    等链表析构时, 链表的原生操作完成后, 再一块释放内存池.
*/

#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000

/// ----------------------------------------------------------------------
/// CLsLinkedList 双链表 定义
/// ----------------------------------------------------------------------
template <typename T>
class CLsLinkedList  
{
public:
    /// ----------------------------------------------------------------------
    /// CLsLinkedNode 定义
    /// ----------------------------------------------------------------------
    
    /// LsDoublyLinkedList's Node
    template <typename T>
        struct CLsLinkedNode
    {
        friend CLsLinkedList<T>; ///< 不需要前向声明, 用到的时候才检查
        friend CLsLinkedList<T>::iterator;

    private:
        CLsLinkedNode(T Elem)
            :m_Elem(Elem)
            ,m_pNext(NULL)
            ,m_pPrev(NULL)
        {
        }
        
        ~CLsLinkedNode()
        {
        }

        T m_Elem; //数据元素
        CLsLinkedNode<T>* m_pPrev; //前驱
        CLsLinkedNode<T>* m_pNext; //后继
    };

    /// ----------------------------------------------------------------------
    /// 正向迭代器 定义
    /// ----------------------------------------------------------------------
    class iterator
    {
        friend class CLsLinkedList<T>;
    public:
        iterator()
        {
            m_pNode = NULL;
        }

        iterator(CLsLinkedNode<T>* pNode)
        {
            m_pNode = pNode;
        }
        
        iterator operator++()
        {
            m_pNode = m_pNode->m_pNext;
            return m_pNode;
        }
        
        iterator operator++(int)
        {
            CLsLinkedNode<T> *pTemp = m_pNode;
            m_pNode = m_pNode->m_pNext;
            return pTemp;
        }

        iterator operator--()
        {
            m_pNode = m_pNode->m_pPrev;
            return m_pNode;
        }
        
        iterator operator--(int)
        {
            CLsLinkedNode<T> *pTemp = m_pNode;
            m_pNode = m_pNode->m_pPrev;
            return pTemp;
        }
        
        T& operator* ()
        {
            return m_pNode->m_Elem;
        }
        
        bool operator!= (const iterator& obj)
        {
            return m_pNode != obj.m_pNode;
        }

        bool operator== (const iterator& obj)
        {
            return m_pNode == obj.m_pNode;
        }

    private:
        CLsLinkedNode<T>* GetNode()
        {
            return m_pNode;
        }

    private:
        CLsLinkedNode<T>* m_pNode;
    };

public:
    iterator begin()
    {
        return m_pHead;
    }

    iterator end()
    {
        return NULL;
    }

public:
    CLsLinkedList();
    virtual ~CLsLinkedList();

    /// 只提供O(1)的接口^_^

    iterator getTail() const;
    iterator getHead() const;
    inline bool isEmpty() const;
    inline size_t getLength() const;  //表长
    void clear();

    iterator addTail(T newElem);
    bool removeTail();

    iterator addHead(T newElem);
    bool removeHead();

    T getAt(iterator it) const;
    void setAt(iterator it, T newElem);
    bool removeAt(iterator it);

    bool insert(iterator it, T newElem);

private:
    CLsLinkedNode<T>* m_pHead;  //头结点
    CLsLinkedNode<T>* m_pTail;  //尾结点
    size_t m_nLength;
};

/// ----------------------------------------------------------------------
/// CLsLinkedList 实现
/// ----------------------------------------------------------------------
template <typename T>
inline size_t CLsLinkedList<T>::getLength() const
{
    return m_nLength;
}

template <typename T>
inline bool  CLsLinkedList<T>::isEmpty() const
{
    return (NULL == m_pHead) ? true : false;
}

template <typename T>
CLsLinkedList<T>::CLsLinkedList()
:m_pHead(NULL)
,m_pTail(NULL)
,m_nLength(0)
{
}

template <typename T>
CLsLinkedList<T>::~CLsLinkedList()
{
    clear();
}

template <typename T>
void CLsLinkedList<T>::clear()
{
    while (!isEmpty())
    {
        removeTail();
    }
}

template <typename T>
T CLsLinkedList<T>::getAt(CLsLinkedList::iterator it) const
{
    return *it;
}

template <typename T>
void CLsLinkedList<T>::setAt(CLsLinkedList::iterator it, T newElem)
{
    *it = newElem;
}

template <typename T>
bool CLsLinkedList<T>::insert(CLsLinkedList::iterator it, T newElem)
{
    CLsLinkedNode<T>* pNewNode = NULL;
    CLsLinkedNode<T>* pPrev = NULL;
    CLsLinkedNode<T>* pNext = NULL;

    pPrev = it.GetNode();
    if (NULL == pPrev)
    {
        return false;
    }

    pNewNode = new CLsLinkedNode<T>(newElem);
    pNext = pPrev->m_pNext;
    
    /*
    1 2 3 [6] 4 5
    3.next = 6
    4.prev = 6
    6.prev = 3
    6.next = 4
    
      1 2 3 4 5 [6]
    */
    pPrev->m_pNext = pNewNode;
    if (NULL != pNext)
    {
        pNext->m_pPrev = pNewNode;
    }

    pNewNode->m_pPrev = pPrev;
    pNewNode->m_pNext = pNext;
    m_nLength++;
    return true;
}

template <typename T>
bool CLsLinkedList<T>::removeTail()
{
    bool bRc = false;
    CLsLinkedNode<T>* pPrev = NULL;

    if (NULL == m_pHead)
    {
        return false;
    }
    
    //1 2 [3]
    if (NULL != m_pTail)
    {
        pPrev = m_pTail->m_pPrev;
        if (NULL != pPrev)
        {
            pPrev->m_pNext = NULL;
        }
        else
        {
            m_pHead = NULL;
        }
        
        delete m_pTail;
        bRc = true;
        m_pTail = pPrev;
        m_nLength--;
    }

    return bRc;
}

template <typename T>
bool CLsLinkedList<T>::removeHead()
{
    if (NULL == m_pHead)
    {
        return false;
    }
    
    //[1] 2 3
    CLsLinkedNode<T>* pNext = m_pHead->m_pNext;
    if (NULL != pNext)
    {
        pNext->m_pPrev = NULL;
    }
    else
    {
        m_pTail = NULL;
    }
    
    delete m_pHead;
    m_nLength--;
    m_pHead = pNext;
    return true;
}

template <typename T>
bool CLsLinkedList<T>::removeAt(CLsLinkedList::iterator it)
{
    CLsLinkedNode<T>* pDelNode = it.GetNode();
    CLsLinkedNode<T>* pPrev = NULL;
    CLsLinkedNode<T>* pNext = NULL;

    if ((NULL == m_pHead) 
        || (NULL == pDelNode))
    {
        return false;
    }
    
    /*
    1 2 [3] 4 5 
    2.next = 4
    4.prev = 2
    
      [1] 2 3 4 5 
      
        1 2 3 4 [5]
        
          [1]
    */
    pPrev = pDelNode->m_pPrev;
    pNext = pDelNode->m_pNext;

    if (NULL != pPrev)
    {
        pPrev->m_pNext = pNext;
    }
    else
    {
        m_pHead = pNext;
    }
    
    if (NULL != pNext)
    {
        pNext->m_pPrev = pPrev;
    }
    else
    {
        m_pTail = pPrev;
    }
    
    delete pDelNode;
    m_nLength--;
    
    return true;
}

template <typename T>
CLsLinkedList<T>::iterator CLsLinkedList<T>::addTail(T newElem)
{
    CLsLinkedList<T>::CLsLinkedNode<T>* pNewNode = new CLsLinkedList<T>::CLsLinkedNode<T>(newElem);
    
    //空表
    if (NULL == m_pHead)
    {
        m_pHead = m_pTail = pNewNode;
    }
    else 
    {
        //1 2 3 4 5 [6]
        //5.next = 6    6.prev = 5  tail = 6
        m_pTail->m_pNext = pNewNode;
        pNewNode->m_pPrev = m_pTail;
        m_pTail = pNewNode;
    }

    m_nLength++;

    return pNewNode;
}

template <typename T>
CLsLinkedList<T>::iterator CLsLinkedList<T>::addHead(T newElem)
{
    CLsLinkedList<T>::CLsLinkedNode<T> *pNewNode = new CLsLinkedList<T>::CLsLinkedNode<T>(newElem);
    
    //空表
    if (NULL == m_pHead)
    {
        m_pHead = m_pTail = pNewNode;
    }
    else 
    {
        //[6] 1 2 3 4 5 
        //1.prev = 6    6.next = 1  head = 6
        m_pHead->m_pPrev = pNewNode;
        pNewNode->m_pNext = m_pHead;
        m_pHead = pNewNode;
    }

    m_nLength++;
    return pNewNode;
}

template <typename T>
CLsLinkedList<T>::iterator CLsLinkedList<T>::getTail() const
{
    return m_pTail;
}

template <typename T>
CLsLinkedList<T>::iterator CLsLinkedList<T>::getHead() const
{
    return m_pHead;
}

#endif // !defined(LSDOUBLYLINKEDLIST_H_82FEA8FE_F7B8_4CD7_A162_751580726632)




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值