• 删除链表节点,删除链表重复节点


    //在O(1)时间内删除链表节点,给定单向链表的一个头指针和一个节点指针,假设该节点一定是链表中的节点
    struct ListNode{
        int m_nValue;
        ListNode* m_pNext;
    };
    void DeleteNode(ListNode** pListHead, ListNode* pToBeDeleted){
        //传入特殊值:空链表,空节点指针
        if (pListHead == nullptr || *pListHead ==nullptr || pToBeDeleted == nullptr)
            return;
        //多节点链表, 删除的不是链表尾节点
        if (pToBeDeleted->m_pNext != nullptr){
            ListNode* pNext = pToBeDeleted->m_pNext;
            pToBeDeleted->m_nValue = pNext->m_nValue;
            pToBeDeleted->m_pNext = pNext->m_pNext;
            delete pNext;
            pNext = nullptr;
        }
        //链表中只有一个节点,删除头节点,要修改头节点指针
        else if(pToBeDeleted == *pListHead){
            *pListHead = nullptr;
            delete pToBeDeleted;
            pToBeDeleted = nullptr;
        }
        //链表中有多个节点,删除尾节点,需要顺序遍历链表找到删除节点的前一个节点
        else{
            ListNode* pNode = *pListHead;
            while (pNode->m_pNext != pToBeDeleted){
                pNode = pNode->m_pNext;
            }
            pNode->m_pNext = nullptr;
            delete pToBeDeleted;
            pToBeDeleted = nullptr;
        }
    }
    
    //删除链表中的重复节点
    void deleteDuplication(ListNode** pListHead){
        if(pListHead == nullptr || *pListHead == nullptr)
            return;
        ListNode* pPreNode = nullptr;
        ListNode* pNode = *pListHead;
        ListNode* pNext;
        while (pNode != nullptr){
            pNext = pNode->m_pNext;
            bool needDelete = false;
            if (pNext != nullptr && pNext->m_nValue == pNode->m_nValue){
                needDelete = true;
            }
            if (!needDelete){
                pPreNode = pNode;
                pNext = pNode->m_pNext;
            }
            else{
                ListNode* pToBeDel = pNode;
                int value = pNode->m_nValue;
                while (pToBeDel != nullptr && pToBeDel->m_nValue == value){
                    pNext = pToBeDel->m_pNext;
                    
                    delete pToBeDel;
                    pToBeDel = nullptr;
                    
                    pToBeDel = pNext;
                }
                if (pPreNode == nullptr)
                    *pListHead = pNext;
                else
                    pPreNode->m_pNext = pNext;
                pNode = pNext;
            }
        }
    }
    
    //链表中倒数第k个节点:只遍历链表一次的解法
    struct ListNode{
        int m_nValue;
        ListNode* m_pNext;
    };
    ListNode* findKthToTail(ListNode* pListHead, unsigned int k){
        if (pListHead == nullptr || k == 0)
            return nullptr;
        ListNode* pAhead = pListHead;
        ListNode* pBehind = nullptr;
        //第一个指针先走k-1步
        for (int i = 0; i < k - 1; ++i){
            //排除链表中节点个数少于k的情况
            if (pAhead->m_pNext != nullptr){
                pAhead = pAhead->m_pNext;
            }
            else
                return nullptr;
        }
        pBehind = pListHead;
        //两个指针同时遍历直到第一个指针到达尾节点停止
        while (pAhead->m_pNext != nullptr){
            pAhead = pAhead->m_pNext;
            pBehind = pBehind->m_pNext;
        }
        return pBehind;
    }
    
    //求链表中间结点:要求只遍历链表一次,两个指针同时出发,
    // 一个指针一次走两步,另一个指针一次走一步,走两步的指针到结尾时候走一步的指针刚好在链表中间
    ListNode* middleNodeOfList(ListNode* pListHead){
        if (pListhead == nullptr)
            return nullptr;
        ListNode* pAhead = pListHead;
        ListNode* pBehind = pListHead;
        while (pAhead->m_pNext != nullptr && pAhead->m_pNext->m_pNext != nullptr){
            pAhead = pAhead->m_pNext->m_pNext;
            pBehind = pBehind->m_pNext;
        }
        return pBehind;
    }
    
    //链表中环的入口:
    //先判断链表是否闭环,返回闭环中一个节点, 不闭环则返回nullptr
    ListNode* meetingNode(ListNode* pHead){
        if (pHead == nullptr)
            return nullptr;
        ListNode* pSlow = pHead->m_pNext;
        if (pSlow == nullptr)
            return nullptr;
        ListNode* pFast = pSlow->m_pNext;
        while (pFast != nullptr && pSlow != nullptr){
            if (pFast == pSlow)
                return pFast;
            else{
                pSlow = pSlow->m_pNext;
                pFast = pFast->m_pNext;
                if (pFast != nullptr)
                    pFast = pFast->m_pNext;
            }
        }
        return nullptr;
    }
    //找到环中任意节点,然后计算环中节点个数,再找出环的入口节点
    ListNode* entryNodeOfList(ListNode* pHead){
        if (pHead == nullptr)
            return nullptr;
        ListNode* pMeetingNode = meetingNode(pHead);
        if (pMeetingNode == nullptr)  //非闭环
            return nullptr;
        //得到环中节点个数
        ListNode* pNode1 = pMeetingNode;
        int nodesInLoop = 1;
        while (pNode1->m_pNext != pMeetingNode){
            pNode1 = pNode1->m_pNext;
            nodesInLoop++;
        }
        //pNode1先走 nodesInLoop 步,
        pNode1 = pHead;
        for (int i = 0; i < nodesInLoop; ++i){
            pNode1 = pNode1->m_pNext;
        }
        //再移动pNode1和pNode2,直到指针相遇,即环入口节点
        ListNode* pNode2 = pHead;
        while (pNode1 != pNode2){
            pNode1 = pNode1->m_pNext;
            pNode2 = pNode2->m_pNext;
        }
        return pNode1;
    }
    
    //反转链表:返回反转后链表的头指针,
    ListNode* reverseList(ListNode* pHead){
        ListNode* pReversedListHead = nullptr;
        ListNode* pPreNode = nullptr;
        ListNode* pNode = pHead;
        while (pNode != nullptr){
            ListNode* pNext = pNode->m_pNext;
            if (pNext == nullptr)
                pReversedListHead = pNode;
            pNode->m_pNext = pPreNode;
            pPreNode = pNode;
            pNode = pNext;
        }
        return pReversedListHead;
    }
    
    //合并两个排序的链表:(1)递归实现
    ListNode* Merge(ListNode* pHead1, ListNode* pHead2){
        if (pHead1 == nullptr)
            return pHead2;
        else if (pHead2 == nullptr)
            return pHead1;
        
        ListNode* pMergedHead = nullptr;
        if (pHead1->m_nValue < pHead2->m_nValue){
            pMergedHead = pHead1;
            pMergedHead->m_pNext = Merge(pHead1->m_pNext, pHead2);
        }
        else{
            pMergedHead = pHead2;
            pMergedHead->m_pNext = Merge(pHead1, pHead2->m_pNext);
        }
        return pMergedHead;
    }
    //合并链表的非递归实现(自己写的^_^):
    ListNode* merge(ListNode* pHead1, ListNode* pHead2){
        if (pHead1 == nullptr)
            return pHead2;
        else if (pHead2 == nullptr)
            return pHead1;
        ListNode* pHead = nullptr;
        ListNode* pNode1 = pHead1;
        ListNode* pNode2 = pHead2;
        ListNode* pPreNode = nullptr;
        if (pHead1->m_nValue < pHead2->m_nValue){
            pHead = pHead1;
            pNode1 = pNode1->m_pNext;
            pPreNode = pHead1;
        }
        else{
            pHead = pHead2;
            pNode1 = pNode2->m_pNext;
            pPreNode = pHead2;
        }
        while (pNode1 != nullptr && pNode2 != nullptr){
            if (pNode1->m_nValue < pNode2->m_nValue){
                pPreNode->m_pNext = pNode1;
                pPreNode = pNode1;
                pNode1 = pNode1->m_pNext;
            }
            else{
                pPreNode->m_pNext = pNode2;
                pPreNode = pNode2;
                pNode2 = pNode2->m_pNext;
            }
        }
        if (pNode1 != nullptr){
            pPreNode->m_pNext = pNode1;
        }
        if (pNode2 != nullptr){
            pPreNode->m_pNext = pNode2;
        }
        return pHead;
    }
    
  • 相关阅读:
    arcgis栅格重分类(Reclassify>Raster To Polygon)
    geotools统计某一shapefile的polygon区域内的值的平均值
    geotools最短路径的实现
    arcgis栅格重采样(降采样)(切图)
    如何生成delaunay三角网(BowyerWatson算法)
    Arcgis自动化制图
    java collection转换为list
    geoserver发布服务流程
    GeoServer发布geotiff并且设置QGIS样式
    halconset_diagonal_matrix设置矩阵的对角线元素
  • 原文地址:https://www.cnblogs.com/songdanzju/p/7442051.html
Copyright © 2020-2023  润新知