//Write a program to concatenate two doubly linked lists X1 and X2. After
// concatenation X1 is a pointer to first node of the resulting lists.

#include <stdio.h>
#include <stdlib.h>

typedef struct node {
    int data;
    struct node *llink;
    struct node *rlink;
} *node_pointer;

void concatenate(node_pointer *X1, node_pointer *X2) {
    node_pointer temp;
    if (*X1 == NULL) {
        *X1 = *X2;
    } else if (*X2 != NULL) {
        temp = *X1;
        while (temp->rlink != NULL)
            temp = temp->rlink;
        temp->rlink = *X2;
        (*X2)->llink = temp;
    }
}

node_pointer create_node(int data) {
    node_pointer new_node = (node_pointer)malloc(sizeof(struct node));
    new_node->data = data;
    new_node->llink = NULL;
    new_node->rlink = NULL;
    return new_node;
}

void insert_end(node_pointer *head, int data) {
    node_pointer new_node = create_node(data);
    if (*head == NULL) {
        *head = new_node;
    } else {
        node_pointer temp = *head;
        while (temp->rlink != NULL)
            temp = temp->rlink;
        temp->rlink = new_node;
        new_node->llink = temp;
    }
}

void print_list(node_pointer head) {
    node_pointer temp = head;
    while (temp != NULL) {
        printf("%d ", temp->data);
        temp = temp->rlink;
    }
    printf("\n");
}

int main() {
    node_pointer X1 = NULL, X2 = NULL;

    insert_end(&X1, 1);
    insert_end(&X1, 2);
    insert_end(&X1, 3);

    insert_end(&X2, 4);
    insert_end(&X2, 5);

    printf("X1: ");
    print_list(X1);
    printf("X2: ");
    print_list(X2);

    concatenate(&X1, &X2);

    printf("After concatenation:\n");
    printf("X1: ");
    print_list(X1);

    return 0;
}
