leetcode(c++)(链表)

#include <iostream>
#include <vector>
#include <unordered_map>

using namespace std;

struct LinkNode
{
    int val_ = 0;
    LinkNode* next = nullptr; 
    LinkNode* random = nullptr;
    LinkNode(int val)
    {
        val_ = val;
    }
};

void print(LinkNode* node)
{    
    while(node != nullptr)
    {
        cout << node->val_ <<" ";
        node = node->next;
    }
    cout << endl;
}

LinkNode* generateLinkNode(const vector<int>& nums)
{
    int n = nums.size(); 
    LinkNode dummy(0);
    LinkNode* head = &dummy;
    for(int i = 0; i < n; ++i)
    {
       
       LinkNode* cur = new LinkNode(nums[i]);
       head->next = cur;    
       head = head->next;
    }
    return dummy.next;
}

LinkNode* removeElements(LinkNode* head,int val)
{
    LinkNode dummy(0);
    dummy.next = head;
    LinkNode* cur = &dummy;
    while(cur->next!=nullptr)
    {
        if(cur->next->val_ == val)cur->next = cur->next->next;
        else cur = cur->next;
    }
    return dummy.next;
}

LinkNode* removeElements_r(LinkNode* head,int val)
{
    if(nullptr == head)return nullptr;
    head->next = removeElements_r(head->next,val);
    return head->val_ == val ?head->next:head;
}

LinkNode* removeDuplicate(LinkNode* head)
{
    LinkNode* cur = head;   
    while(cur != nullptr)
    {
        while(cur->next != nullptr && cur->next->val_ == cur->val_)
        {
            cur->next = cur->next->next;
        }
        cur  = cur->next;
    }
    return head;
}

LinkNode* removeDuplicate_r(LinkNode* head)
{
    if(nullptr == head || nullptr == head->next)return head;
    head->next = removeDuplicate_r(head->next);
    return head->next->val_ == head->val_ ? head->next:head;
}

LinkNode* deleteDuplicate(LinkNode* head)
{
    LinkNode dummy(0);
    dummy.next = head;
    LinkNode* cur = head;
    LinkNode* pre = &dummy;
    while(cur != nullptr && cur->next != nullptr)
    {
        if(cur->val_ == cur->next->val_)
        {
            int tmp = cur->val_;
            while(cur != nullptr && tmp == cur->val_)cur = cur->next;
            pre->next = cur;
        }
        else
        {
            pre = pre->next;
            cur = cur->next;
        }
    }
    return dummy.next;
}

LinkNode* removeNthFromEnd(LinkNode* head,int n)
{
    LinkNode dummy(0);
    dummy.next = head;
    LinkNode* first = &dummy, *second = &dummy;
    for(int i = 1; i <= n + 1; ++i)
    {
        first = first->next;
    }
    while(first != nullptr)
    {
        first = first->next;
        second = second->next;
    }
    second->next = second->next->next;
    return dummy.next;
}

LinkNode* removeZeroSumSubList(LinkNode* head)
{
    int preFix = 0;
    LinkNode dummy(0);
    dummy.next = head;
    unordered_map<int,LinkNode*>map;
    map[0] = &dummy;
    for(LinkNode* i = &dummy; i != nullptr; i = i->next)
    {
        preFix+=i->val_;
        map[preFix] = i;
    }
    preFix = 0;
    for(LinkNode* i = &dummy;i != nullptr; i = i->next)
    {
        preFix += i->val_;
        i->next = map[preFix]->next;
    }
    return dummy.next;
}

LinkNode* endOfFirst(LinkNode* head)
{
    LinkNode* slow = head;
    LinkNode* fast = head;
    while(fast->next != nullptr && fast->next->next != nullptr)
    {
        fast = fast->next->next;
        slow = slow->next;
    }
    return slow;
}

LinkNode* reverse(LinkNode* head)
{
    LinkNode* pre = nullptr;
    while(head != nullptr)
    {
        LinkNode* next = head->next;
        head->next = pre;
        pre = head;
        head = next;
    }
    return pre;
}

bool isPalindrome(LinkNode* head)
{

    LinkNode* firstHead = endOfFirst(head);
    LinkNode* second = reverse(firstHead->next);
    LinkNode* p1 = head;
    LinkNode* p2 = second;
    bool result = true;
    while(result && p2 != nullptr)
    {
        if(p1->val_ != p2->val_)return false;
        p1 = p1->next;
        p2 = p2->next;
    }
    firstHead->next = reverse(second);
    return result;
}

int length(LinkNode* head)
{
    int size = 0;
    while(head != nullptr)
    {
        ++size;
        head = head->next;
    }
    return size;
}

LinkNode* getInersection(LinkNode* headA, LinkNode* headB)
{
    
    int lenA = length(headA), lenB = length(headB);
    while(lenB > lenA)
    {
        headB = headB->next;
        --lenB;
    }
    while(lenA > lenB)
    {
        headA = headA->next;
        --lenA;
    }
    while(headA != nullptr&& headB != nullptr)
    {
        if(headA->val_ == headB->val_)return headA;
        headA = headA->next;
        headB = headB->next;
    }
    return nullptr;    
}

LinkNode* copyRandom(LinkNode* head)
{
    unordered_map<LinkNode* ,LinkNode*>map;
    for(LinkNode* i = head; i != nullptr; i = i->next)
    {
        map[i] = new LinkNode(i->val_);
    }
    for(LinkNode* cur = head; cur != nullptr; cur = cur->next)
    {
        map[cur]->next = map[cur->next];
        map[cur]->random = map[cur->random];
    }
    return map[head];
}

LinkNode* reverse(LinkNode* head,LinkNode* newHead)
{
    if(nullptr == head)return newHead;
    LinkNode* next = head->next;
    head->next = newHead;
    return reverse(next,head);
}

LinkNode* reverseBetween(LinkNode* head,int m, int n)
{
    LinkNode dummy(-1);
    dummy.next = head;
    LinkNode* pre = &dummy;
    LinkNode* cur = dummy.next;
    int i = 1;
    while(i < m)
    {
        pre = cur;
        cur = cur->next;
        ++i;
    }
    LinkNode* node = pre;
    while(i ++ <= n)
    {
        LinkNode* next = cur->next;
        cur->next = pre;
        pre = cur;
        cur = next;
    }
    node->next->next = cur;
    node->next = pre;
    return dummy.next;
}

LinkNode* reverseKGroup(LinkNode* head, int k)
{
    LinkNode* node = head;
    int cnt = 0;
    while(cnt < k)
    {        
        if(nullptr == node)return head;
        node = node->next;
        ++cnt;        
    }    
    LinkNode* pre = reverseKGroup(node,k);
    while(cnt-- > 0)
    {
        LinkNode* next = head->next;
        head->next = pre;
        pre = head;
        head = next;
    }       
    return pre;    
}

LinkNode* addTwoNumbers(LinkNode* l1, LinkNode* l2)
{
    LinkNode dummy(0);
    LinkNode* cur = &dummy;
    int carry = 0;
    while(l1 != nullptr || l2 != nullptr || carry == 1)
    {
        int sum = (l1 == nullptr ? 0 :l1->val_) + (l2 == nullptr ? 0 : l2->val_) + carry;
        cur->next = new LinkNode(sum % 10);
        carry = sum / 10;
        if(l1!= nullptr)l1 = l1->next;
        if(l2!= nullptr)l2 = l2->next;
        cur = cur->next;
    }
    return dummy.next;
}

LinkNode* mergeTwoLists(LinkNode* l1, LinkNode* l2)
{
    LinkNode dummy(0);
    LinkNode* cur = &dummy;
    while(l1 != nullptr && l2 != nullptr)
    {
        if(l1->val_ < l2->val_)
        {
            cur->next = l1;
            l1 = l1->next;
        }
        else
        {
            cur->next = l2;
            l2 = l2->next;
        }
        cur = cur->next;
    }
    cur->next = l1 == nullptr ? l2:l1;
    return dummy.next;
}

LinkNode* partition(const vector<LinkNode*>& lists,int start, int end)
{
    if(start == end)return lists[start];
    if(start < end)
    {
        int mid = start + (end - start) / 2;
        auto l1 = partition(lists,start,mid);
        auto l2 = partition(lists,mid+1,end);
        return mergeTwoLists(l1,l2);
    }
    return nullptr;
}

LinkNode* mergeKLists(const vector<vector<int>>& lists)
{
    vector<LinkNode*>listss;
    for(int i = 0; i < lists.size(); ++i)
    {
        listss.push_back(generateLinkNode(lists[i]));
    }
    return partition(listss,0,lists.size() - 1);
}

bool hasCycleNode(LinkNode* head)
{
    LinkNode* slow = head, *fast = head;
    while(fast != nullptr && fast->next != nullptr)
    {
        slow = slow->next;
        fast = fast->next->next;
        if(slow == fast) return true;
    }
    return false;
}

LinkNode* detectCycleNode(LinkNode* head)
{
    LinkNode* slow = head, *fast = head;
    while(fast != nullptr && fast->next != nullptr)
    {
        fast = fast->next->next;
        slow = slow->next;
        if(fast == slow)
        {
            fast = head;
            while(fast != slow)
            {
                fast = fast->next;
                slow = slow->next;
            }
            return slow;
        }
    }
    return nullptr;
}

int findDuplicate(const vector<int>& nums)
{
    int slow = nums[0];
    int fast = nums[0];
    while(true)
    {
        slow = nums[slow];
        fast = nums[nums[fast]];
        if(slow == fast)
        {
            fast = nums[0];
            while(fast != slow)
            {
                slow = nums[slow];
                fast = nums[fast];
            }
            return slow;
        }
    }
    return -1;
}

int main()
{
    //LeetCode203
    vector<int>nums{1,2,6,3,4,5,6};
    int val = 6;
    auto node = generateLinkNode(nums);
    // print(removeElements(node,val));
    print(removeElements_r(node,val));

    //LeetCode83
    nums = {1,1,2};
    node = generateLinkNode(nums);
    // print(removeDuplicate(node));
    print(removeDuplicate_r(node));

    //LeetCode82
    nums = {1,2,3,3,4,4,5};
    node = generateLinkNode(nums);
    print(deleteDuplicate(node));

    //LeetCode19
    nums = {1,2,3,4,5};
    int n = 2;
    node = generateLinkNode(nums);
    print(removeNthFromEnd(node,n));

    //LeetCode1171
    nums = {1,2,-3,3,1};
    print(removeZeroSumSubList(generateLinkNode(nums)));

    //LeetCode234
    nums = {1,2,2,1};
    cout << isPalindrome(generateLinkNode(nums)) << endl;

    //LeetCode160

    vector<int>listA{4,1,8,4,5};
    vector<int>listB{5,6,1,8,4,5};    
    cout << getInersection(generateLinkNode(listA),generateLinkNode(listB))->val_ << endl;

    //LeetCode206

    nums = {1,2,3,4,5};
    print(reverse(generateLinkNode(nums)));
    print(reverse(generateLinkNode(nums),nullptr));

    //LeetCode92
    nums = {1,2,3,4,5};
    int left = 2, right = 4;
    print(reverseBetween(generateLinkNode(nums),left,right));

    //LeetCode25
    nums = {1,2,3,4,5};
    int k = 2;
    print(reverseKGroup(generateLinkNode(nums),k));

    //LeetCode2
    auto l1 = {2,4,3};
    auto l2 = {5,6,4};
    print(addTwoNumbers(generateLinkNode(l1),generateLinkNode(l2)));

    //LeetCode445
    l1 = {7,2,4,3};
    l2 = {5,6,4};
    print(reverse(addTwoNumbers(reverse(generateLinkNode(l1)),reverse(generateLinkNode(l2)))));

    //LeetCode21
    l1 = {1,2,4};
    l2 = {1,3,4};
    print(mergeTwoLists(generateLinkNode(l1),generateLinkNode(l2)));

    //LeetCode23
    vector<vector<int>> lists = {{1,4,5},{1,3,4},{2,6}};
    print(mergeKLists(lists));

    //LeetCode141
    LinkNode n1(3);
    LinkNode n2(2);
    LinkNode n3(0);
    LinkNode n4(-4);
    n1.next = &n2;
    n2.next = &n3;
    n3.next = &n4;
    n4.next = &n2;
    cout << hasCycleNode(&n1) << endl;

    //LeetCode142
    cout << detectCycleNode(&n1)->val_ << endl;

    //LeetCode287
    nums = {1,3,4,2,2};
    cout << findDuplicate(nums) << endl;
    
    return 0;
}

 

posted @ 2022-05-04 20:02  fourmii  阅读(43)  评论(0编辑  收藏  举报