Check linked list with a loop is palindrome or not
Given a linked list with a loop, the task is to find whether it is palindrome or not. You are not allowed to remove the loop.
Examples:
Input : 1 -> 2 -> 3 -> 2 /|\ \|/ ------- 1 Output: Palindrome Linked list is 1 2 3 2 1 which is a palindrome. Input : 1 -> 2 -> 3 -> 4 /|\ \|/ ------- 1 Output: Palindrome Linked list is 1 2 3 4 1 which is a not palindrome.
Algorithm:
- Detect the loop using Floyd Cycle Detection Algorithm.
- Then find the starting node of loop as discussed in this
- Check linked list is palindrome or not as discussed in this
Below is the implementation.
C++
// C++ program to check if a linked list with // loop is palindrome or not. #include<bits/stdc++.h> using namespace std; /* Link list node */ struct Node { int data; struct Node * next; }; /* Function to find loop starting node. loop_node --> Pointer to one of the loop nodes head --> Pointer to the start node of the linked list */ Node* getLoopstart(Node *loop_node, Node *head) { Node *ptr1 = loop_node; Node *ptr2 = loop_node; // Count the number of nodes in loop unsigned int k = 1, i; while (ptr1->next != ptr2) { ptr1 = ptr1->next; k++; } // Fix one pointer to head ptr1 = head; // And the other pointer to k nodes after head ptr2 = head; for (i = 0; i < k; i++) ptr2 = ptr2->next; /* Move both pointers at the same pace, they will meet at loop starting node */ while (ptr2 != ptr1) { ptr1 = ptr1->next; ptr2 = ptr2->next; } return ptr1; } /* This function detects and find loop starting node in the list*/ Node* detectAndgetLoopstarting(Node *head) { Node *slow_p = head, *fast_p = head,*loop_start; //Start traversing list and detect loop while (slow_p && fast_p && fast_p->next) { slow_p = slow_p->next; fast_p = fast_p->next->next; /* If slow_p and fast_p meet then find the loop starting node*/ if (slow_p == fast_p) { loop_start = getLoopstart(slow_p, head); break ; } } // Return starting node of loop return loop_start; } // Utility function to check if a linked list with loop // is palindrome with given starting point. bool isPalindromeUtil(Node *head, Node* loop_start) { Node *ptr = head; stack< int > s; // Traverse linked list until last node is equal // to loop_start and store the elements till start // in a stack int count = 0; while (ptr != loop_start || count != 1) { s.push(ptr->data); if (ptr == loop_start) count = 1; ptr = ptr->next; } ptr = head; count = 0; // Traverse linked list until last node is // equal to loop_start second time while (ptr != loop_start || count != 1) { // Compare data of node with the top of stack // If equal then continue if (ptr->data == s.top()) s.pop(); // Else return false else return false ; if (ptr == loop_start) count = 1; ptr = ptr->next; } // Return true if linked list is palindrome return true ; } // Function to find if linked list is palindrome or not bool isPalindrome(Node* head) { // Find the loop starting node Node* loop_start = detectAndgetLoopstarting(head); // Check if linked list is palindrome return isPalindromeUtil(head, loop_start); } Node *newNode( int key) { Node *temp = new Node; temp->data = key; temp->next = NULL; return temp; } /* Driver program to test above function*/ int main() { Node *head = newNode(50); head->next = newNode(20); head->next->next = newNode(15); head->next->next->next = newNode(20); head->next->next->next->next = newNode(50); /* Create a loop for testing */ head->next->next->next->next->next = head->next->next; isPalindrome(head)? cout << "\nPalindrome" : cout << "\nNot Palindrome" ; return 0; } |
chevron_right
filter_none
Java
// Java program to check if a linked list // with loop is palindrome or not. import java.util.*; class GfG { /* Link list node */ static class Node { int data; Node next; } /* Function to find loop starting node. loop_node --> Pointer to one of the loop nodes head --> Pointer to the start node of the linked list */ static Node getLoopstart(Node loop_node, Node head) { Node ptr1 = loop_node; Node ptr2 = loop_node; // Count the number of nodes in loop int k = 1 , i; while (ptr1.next != ptr2) { ptr1 = ptr1.next; k++; } // Fix one pointer to head ptr1 = head; // And the other pointer to k // nodes after head ptr2 = head; for (i = 0 ; i < k; i++) ptr2 = ptr2.next; /* Move both pointers at the same pace, they will meet at loop starting node */ while (ptr2 != ptr1) { ptr1 = ptr1.next; ptr2 = ptr2.next; } return ptr1; } /* This function detects and find loop starting node in the list*/ static Node detectAndgetLoopstarting(Node head) { Node slow_p = head, fast_p = head,loop_start = null ; //Start traversing list and detect loop while (slow_p != null && fast_p != null && fast_p.next != null ) { slow_p = slow_p.next; fast_p = fast_p.next.next; /* If slow_p and fast_p meet then find the loop starting node*/ if (slow_p == fast_p) { loop_start = getLoopstart(slow_p, head); break ; } } // Return starting node of loop return loop_start; } // Utility function to check if // a linked list with loop is // palindrome with given starting point. static boolean isPalindromeUtil(Node head, Node loop_start) { Node ptr = head; Stack<Integer> s = new Stack<Integer> (); // Traverse linked list until last node // is equal to loop_start and store the // elements till start in a stack int count = 0 ; while (ptr != loop_start || count != 1 ) { s.push(ptr.data); if (ptr == loop_start) count = 1 ; ptr = ptr.next; } ptr = head; count = 0 ; // Traverse linked list until last node is // equal to loop_start second time while (ptr != loop_start || count != 1 ) { // Compare data of node with the top of stack // If equal then continue if (ptr.data == s.peek()) s.pop(); // Else return false else return false ; if (ptr == loop_start) count = 1 ; ptr = ptr.next; } // Return true if linked list is palindrome return true ; } // Function to find if linked list // is palindrome or not static boolean isPalindrome(Node head) { // Find the loop starting node Node loop_start = detectAndgetLoopstarting(head); // Check if linked list is palindrome return isPalindromeUtil(head, loop_start); } static Node newNode( int key) { Node temp = new Node(); temp.data = key; temp.next = null ; return temp; } /* Driver code*/ public static void main(String[] args) { Node head = newNode( 50 ); head.next = newNode( 20 ); head.next.next = newNode( 15 ); head.next.next.next = newNode( 20 ); head.next.next.next.next = newNode( 50 ); /* Create a loop for testing */ head.next.next.next.next.next = head.next.next; if (isPalindrome(head) == true ) System.out.println( "Palindrome" ); else System.out.println( "Not Palindrome" ); } } // This code is contributed by prerna saini |
chevron_right
filter_none
C#
// C# program to check if a linked list // with loop is palindrome or not. using System; using System.Collections.Generic; class GfG { /* Link list node */ class Node { public int data; public Node next; } /* Function to find loop starting node. loop_node --> Pointer to one of the loop nodes head --> Pointer to the start node of the linked list */ static Node getLoopstart(Node loop_node, Node head) { Node ptr1 = loop_node; Node ptr2 = loop_node; // Count the number of nodes in loop int k = 1, i; while (ptr1.next != ptr2) { ptr1 = ptr1.next; k++; } // Fix one pointer to head ptr1 = head; // And the other pointer to k // nodes after head ptr2 = head; for (i = 0; i < k; i++) ptr2 = ptr2.next; /* Move both pointers at the same pace, they will meet at loop starting node */ while (ptr2 != ptr1) { ptr1 = ptr1.next; ptr2 = ptr2.next; } return ptr1; } /* This function detects and find loop starting node in the list*/ static Node detectAndgetLoopstarting(Node head) { Node slow_p = head, fast_p = head,loop_start = null ; //Start traversing list and detect loop while (slow_p != null && fast_p != null && fast_p.next != null ) { slow_p = slow_p.next; fast_p = fast_p.next.next; /* If slow_p and fast_p meet then find the loop starting node*/ if (slow_p == fast_p) { loop_start = getLoopstart(slow_p, head); break ; } } // Return starting node of loop return loop_start; } // Utility function to check if // a linked list with loop is // palindrome with given starting point. static bool isPalindromeUtil(Node head, Node loop_start) { Node ptr = head; Stack< int > s = new Stack< int > (); // Traverse linked list until last node // is equal to loop_start and store the // elements till start in a stack int count = 0; while (ptr != loop_start || count != 1) { s.Push(ptr.data); if (ptr == loop_start) count = 1; ptr = ptr.next; } ptr = head; count = 0; // Traverse linked list until last node is // equal to loop_start second time while (ptr != loop_start || count != 1) { // Compare data of node with the top of stack // If equal then continue if (ptr.data == s.Peek()) s.Pop(); // Else return false else return false ; if (ptr == loop_start) count = 1; ptr = ptr.next; } // Return true if linked list is palindrome return true ; } // Function to find if linked list // is palindrome or not static bool isPalindrome(Node head) { // Find the loop starting node Node loop_start = detectAndgetLoopstarting(head); // Check if linked list is palindrome return isPalindromeUtil(head, loop_start); } static Node newNode( int key) { Node temp = new Node(); temp.data = key; temp.next = null ; return temp; } /* Driver code*/ public static void Main(String[] args) { Node head = newNode(50); head.next = newNode(20); head.next.next = newNode(15); head.next.next.next = newNode(20); head.next.next.next.next = newNode(50); /* Create a loop for testing */ head.next.next.next.next.next = head.next.next; if (isPalindrome(head) == true ) Console.WriteLine( "Palindrome" ); else Console.WriteLine( "Not Palindrome" ); } } /* This code is contributed by 29AjayKumar */ |
chevron_right
filter_none
Output:
Palindrome
This article is contributed by Sahil Chhabra (akku). If you like GeeksforGeeks and would like to contribute, you can also write an article using contribute.geeksforgeeks.org or mail your article to contribute@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.
Please write comments if you find anything incorrect, or you want to share more information about the topic discussed above.
Recommended Posts:
- Function to check if a singly linked list is palindrome
- Check if a doubly linked list of characters is palindrome or not
- Check if a linked list of strings forms a palindrome
- Length of longest palindrome list in a linked list using O(1) extra space
- Detect loop in a linked list
- Make a loop at k-th position in a linked list
- Detect and Remove Loop in a Linked List
- Find first node of loop in a linked list
- Find length of loop in linked list
- Check if a linked list is Circular Linked List
- Check whether the length of given linked list is Even or Odd
- Check if a Linked List is Pairwise Sorted
- Check if a pair with given product exists in Linked list
- Check if linked list is sorted (Iterative and Recursive)
- Check if elements of Linked List are present in pair