Copy a linked list with a random pointer

Source: Internet
Author: User

In addition to the next pointer, a single-chain table also has a random pointer pointing to any element in the linked list.

How to copy such a linked list?

It is easy to copy a chain through next. The difficulty is how to properly set the random pointer in the new linked list. For this purpose, we need to establish a connection between the old linked list and the corresponding node of the new linked list. In addition to the linked list, we can use extra pointers in the linked list to link up the storage space.

Let's just move on to the code. It is only possible that a pointer is not necessarily used for some purpose, but the idea is similar.

#include <cstdio>#include <cstdlib>#include <ctime>#include <cassert>using namespace std;struct Node {    int val;    struct Node *next;    struct Node *random;    Node(int val_, Node *next_, Node *random_)        : val(val_), next(next_), random(random_) { }    Node (int val_)        : val(val_), next(NULL), random(NULL) { }    Node () // for the head nodes.        : val(-1), next(NULL), random(NULL) { }};#define NR_NODES    10// Setup a linked-list with random pointervoid setup_random_linked_list(struct Node *head){    Node *curr;    Node *all_nodes[NR_NODES];    int i;    // allocate all the nodes.    for (i = NR_NODES - 1; i >= 0; i--) {        curr = new Node(i, head->next, NULL);        head->next = curr;        all_nodes[i] = curr;    }    // setup the random pointers in each node.    srand(time(0));    curr = head->next;    while (curr) {        curr->random = all_nodes[rand() % NR_NODES];        curr = curr->next;    }}// free the listvoid free_random_linked_list(struct Node *head){    Node *curr, *temp;    curr = head->next;    while (curr) {        temp = curr->next;        delete curr;        curr = temp;    }}void print_random_linked_list(struct Node *head){    Node *curr;    curr = head->next;    while (curr) {        printf("%d ", curr->val);        curr = curr->next;    }    printf("\n");    curr = head->next;    while (curr) {        printf("%d ", curr->random->val);        curr = curr->next;    }    printf("\n");}// copy from list @src to list @dst.void copy_random_linked_list(struct Node *dst, struct Node *src){    // Image that there're 4 parallel lists...    Node *curr_src, *curr_dst;    // 1, duplicate the list.    curr_src = src->next;    while (curr_src) {        // copy the node        curr_dst = new Node(curr_src->val);        // 'random' vertically goes down, while 'next' goes up to original's random.        curr_dst->next = curr_src->random;        curr_src->random = curr_dst;        // move forward        curr_src = curr_src->next;    }    // 2, Now that 'random' comes vertically form the original list to the duplicated list,     // and that 'next' points to the random node in the old list,    // use that to setup the 'random' pointer in the new list.    curr_src = src->next;    dst->next = curr_src->random; // follow the head node.    while (curr_src) {        curr_dst = curr_src->random;        // setup 'random' relationship via the original list.        curr_dst->random = curr_dst->next->random;        // move forward        curr_src = curr_src->next;    }    // 3, now the vertical links still exist, and 'next's in the new list point to 'random'     // in the original list, go through the lists to repair both.    curr_src = src->next;    while (curr_src) {        curr_dst = curr_src->random;        // setup 'next' relationship via the original list.        curr_src->random = curr_dst->next;        curr_dst->next = curr_src->next ? curr_src->next->random : NULL;        // move forward        curr_src = curr_src->next;    }}int main(int argc, char *argv[]){    Node head, head2;    setup_random_linked_list(&head);    printf("the original list before copying: \n");    print_random_linked_list(&head);    copy_random_linked_list(&head2, &head);    printf("finished copying random linked list.\n");    printf("the original list after copying: \n");    print_random_linked_list(&head);    printf("and the duplicated list: \n");    print_random_linked_list(&head2);    free_random_linked_list(&head);    free_random_linked_list(&head2);    return 0;}

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.