20200909: Under the collection of linked list questions

Under the collection of linked list topics

topic

1.138. Copy linked list with random pointer
Insert picture description here
2.21. Merge two ordered linked lists
Insert picture description here
3.23. Merge K ascending linked lists
Insert picture description here

Ideas and algorithms

  1. Go back to the meaning of the deep copy topic and read it clearly. You need to find out which node the random pointer points to. This is the key. It is clearer to use map to map, and the code problem solutions in two languages ​​of cpp and java are attached.
  2. The idea of ​​merging linked lists is roughly the same. For 21, merging two linked lists, two methods are nothing more than using dummy_head methods or using recursion to achieve. See the code for details. For 23, you can use the sorting method, and the sorting is based on the size of val. Sort them first, and then connect them.

Code

1.138. Copy linked list with random pointer
C++

/*
// Definition for a Node.
class Node {
public:
    int val;
    Node* next;
    Node* random;
    
    Node(int _val) {
        val = _val;
        next = NULL;
        random = NULL;
    }
};
*/

class Solution {
    
    
public:
    Node* copyRandomList(Node* head) {
    
    
        std::map<Node*,int> node_map;
        std::vector<Node*> node_vector;
        Node* ptr = head;
        int i = 0;
        while (ptr) {
    
    
            node_vector.push_back(new Node(ptr->val));
            node_map[ptr] = i;
            ptr = ptr->next;
            i++;
        }
        node_vector.push_back(0);
        ptr = head;
        i = 0;
        while (ptr) {
    
    
            node_vector[i]->next = node_vector[i+1];
            if (ptr->random) {
    
    
                int id = node_map[ptr->random];
                node_vector[i]->random = node_vector[id];
            }
            ptr = ptr->next;
            i++;
        }
        return node_vector[0];
    }
};

Java

/*
// Definition for a Node.
class Node {
    int val;
    Node next;
    Node random;

    public Node(int val) {
        this.val = val;
        this.next = null;
        this.random = null;
    }
}
*/

class Solution {
    
    
    public Node copyRandomList(Node head) {
    
    
        if(head==null) {
    
    
            return null;
        }
        
        Map<Node,Node> map = new HashMap<Node,Node>();
        Node p = head;
        
        while(p!=null) {
    
    
            Node newNode = new Node(p.val);
            map.put(p,newNode);
            p = p.next;
        }
        p = head;
        
        while(p!=null) {
    
    
            Node newNode = map.get(p);
            
            if(p.next!=null) {
    
    
                newNode.next = map.get(p.next);
            }
           
            if(p.random!=null) {
    
    
                newNode.random = map.get(p.random);
            }
            p = p.next;
        }
        
        return map.get(head);
    }
}

2.21. Combine two ordered linked lists
Recursive cpp:

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode() : val(0), next(nullptr) {}
 *     ListNode(int x) : val(x), next(nullptr) {}
 *     ListNode(int x, ListNode *next) : val(x), next(next) {}
 * };
 */
class Solution {
    
    
public:
    ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) {
    
    
        ListNode *dummy_head = nullptr;
        if (l1 == nullptr) {
    
    
            return l2;
        } 
        if (l2 == nullptr) {
    
    
            return l1;
        }
        if (l1->val > l2->val) {
    
    
            dummy_head = l2;
            dummy_head->next = mergeTwoLists(l1,l2->next);
        } else {
    
    
            dummy_head = l1;
            dummy_head->next = mergeTwoLists(l1->next,l2);
        }
        return dummy_head;
    }
};

Recursive java:

/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode(int x) { val = x; }
 * }
 */
class Solution {
    
    
    public ListNode mergeTwoLists(ListNode l1, ListNode l2) {
    
    
        ListNode head = null;
        if (l1 == null) {
    
    
            return l2;
        }
        if (l2 == null) {
    
    
            return l1;
        }

        if (l1.val <= l2.val) {
    
    
            head = l1;
            head.next = mergeTwoLists(l1.next,l2);
        }else{
    
    
            head = l2;
            head.next = mergeTwoLists(l1,l2.next);
        }
        return head;
    }
}

Dummy node method cpp:

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode() : val(0), next(nullptr) {}
 *     ListNode(int x) : val(x), next(nullptr) {}
 *     ListNode(int x, ListNode *next) : val(x), next(next) {}
 * };
 */
class Solution {
    
    
public:
    ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) {
    
    
        ListNode dummy_head(0);
        ListNode* pre = &dummy_head;
        while (l1 && l2) {
    
    
            if (l1->val > l2->val) {
    
    
                pre->next = l2;
                l2 = l2->next;
            } else {
    
    
                pre->next = l1;
                l1 = l1->next;
            }
            pre = pre->next;
        }
        if (l1) {
    
    
            pre->next = l1;
        }
        if (l2) {
    
    
            pre->next = l2;
        }
        return dummy_head.next;
    }
};

3.23. Merge K ascending linked lists
to realize the reconnection of cpp sorting:

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode(int x) : val(x), next(NULL) {}
 * };
 */

 bool cmp(const ListNode* a,const ListNode* b){
    
    
     return a->val < b->val;
 }
class Solution {
    
    
public:
    ListNode* mergeKLists(vector<ListNode*>& lists) {
    
    
        std::vector<ListNode*> node_vec;
        // 把所有链表的节点存入node_vec
        for (int i = 0;i < lists.size();i++) {
    
    
            ListNode* head = lists[i];
            while (head) {
    
    
                node_vec.push_back(head);
                head = head->next;
            }
        }

        // 进行排序并连接即可
        if (node_vec.size() == 0) {
    
    
            return NULL;
        }

        std::sort(node_vec.begin(),node_vec.end(),cmp);
        for (int i = 1;i < node_vec.size();i++) {
    
    
            node_vec[i-1]->next = node_vec[i];
        }
        node_vec[node_vec.size()-1]->next = NULL;
        return node_vec[0];
    }
};

Write at the end

The complexity is basically the complexity of the sorting function, so I won't go into the details anymore!

Guess you like

Origin blog.csdn.net/qq_36828395/article/details/108486407