Program to check string is palindrome or not with equivalent pairs in Python

Suppose we have a lowercase alphabet string called s and also have a list of pairs called 'pairs'. Each element in pairs has two strings [a, b] where the character 'a' and 'b' are considered same. If there are two pairs like [a, b] and [b, c], then we can say a and b are equivalent also b and c are equivalent, so a and c are also equivalent. And any value a or b is equivalent to itself. We have to check whether s is a palindrome or not with the given equivalence relations.

So, if the input is like s = "raceckt" pairs = [["r", "t"], ["a", "k"], ["z", "x"]], then the output will be True, because "a" = "k", and "r" = "t" so the string can be "racecar" which is palindrome.

To solve this, we will follow these steps −

  • g := adjacency list of a graph where list may contain duplicate elements
  • G := adjacency list of a graph where will not contain duplicate elements
    • for each x, y in pairs, do
    • insert x at the end of g[x]
    • insert y at the end of g[y]
    • insert y at the end of g[x]
    • insert x at the end of g[y]
  • Define a function dfs() . This will take a, so_far
  • insert a into so_far
  • for each elem in g[a], do
    • if elem is not in so_far, then
      • dfs(elem, so_far)
  • From the main method, do the following −
  • for each key in g, do
    • dfs(key, G[key])
    • for i in range 0 to floor of(size of s / 2), do
      • if s[i] is same as s[size of s -1-i] or (s[i] is in G[s[size of s - 1-i]] or s[-1 - i] in G[s[i]]) , then
        • go for next iteration
      • otherwise,
        • return False
  • return True


Let us see the following implementation to get better understanding −

from collections import defaultdict
def solve(s, pairs):
   g = defaultdict(list)
   G = defaultdict(set)
   for x, y in pairs:

   def dfs(a, so_far):
      for elem in g[a]:
         if elem not in so_far:
            dfs(elem, so_far)

   for key in g:
      dfs(key, G[key])

   for i in range(0, len(s) // 2):
      if s[i] == s[-1 - i] or (s[i] in G[s[-1 - i]] or s[-1 - i] in G[s[i]]):
         return False
   return True

s = "raceckt"
pairs = [["r", "t"], ["a", "k"], ["z", "x"]]
print(solve(s, pairs))


"raceckt", [["r", "t"], ["a", "k"], ["z", "x"]]