Grupa przesunięty ciąg

Grupa przesunięty ciąg
Wypróbuj w praktyce GfG

Mając tablicę ciągów (wszystkie małe litery) zadaniem jest pogrupować je w taki sposób, aby wszystkie ciągi w grupie były swoimi przesuniętymi wersjami.

Dwa sznurki s1 I s2 nazywane są przesuniętymi, jeśli spełnione są następujące warunki:

  • s1.długość jest równe s2.długość
  • s1[i] jest równe s2[i] + M dla wszystkich 1 <= i <= s1.length for a  stały  liczba całkowita m. Rozważ przesunięcie jako cykliczne, to znaczy, jeśli s2[i] + m > „z”, to zacznij od „a” lub jeśli s2[i] + m < 'a' then start from 'z'.

Przykłady:

Wejście: arr[] = ['acd' 'dfg' 'wyz' 'yab' 'mop' 'bdfh' 'a' 'x' 'moqs']
Wyjście: [ ['acd' 'dfg' 'wyz' 'yab' 'mop'] ['bdfh' 'moqs'] ['a' 'x'] ]
Wyjaśnienie: Wszystkie przesunięte ciągi są grupowane razem.

Wejście: arr = ['geek' 'dla' 'geek']
Wyjście: [['dla'] ['geek'] ['geek']]

Podejście: użycie mapy mieszającej

Pomysł jest taki, aby wygenerować unikat haszysz dla każdej grupy wg normalizowanie sznurki. Tutaj normalizowanie oznacza zwrócenie pierwszego znaku każdego ciągu znaków na „a” poprzez obliczenie wymaganej wartości zmiany i stosując go równomiernie do wszystkich znaków w moda cykliczna .
Przykład: s = „dca” przesunięcia = „d” - „a” = 3
znaki znormalizowane: „d” – 3 = „a” „c” – 3 = „z” i „a” – 3 = „x”
znormalizowany ciąg = „azx”

The znormalizowany ciąg (hash) reprezentuje wzór zmiany tak, że ciągi o tym samym wzorze mają ten sam skrót. Używamy mapy skrótów do śledzenia tych skrótów i mapowania ich do odpowiednich grup. Dla każdego ciągu obliczamy skrót i używamy go do utworzenia nowej grupy lub dodania ciągu do istniejącej grupy w jednym przejściu.

C++
   // C++ program to print groups of shifted strings   // together using Hash Map   #include          #include         #include         using     namespace     std  ;   // Function to generate hash by shifting and equating    // the first character   string     getHash  (  string     s  )     {          // Calculate the shift needed to normalize the string      int     shifts     =     s  [  0  ]     -     'a'  ;         for     (  char     &  ch     :     s  )     {         // Adjust each character by the shift      ch     =     ch     -     shifts  ;             // Wrap around if the character goes below 'a'      if     (  ch      <     'a'  )         ch     +=     26  ;         }      return     s  ;   }   // Function to group shifted string together   vector   <  vector   <  string  >>     groupShiftedString  (  vector   <  string  >     &  arr  )     {      vector   <  vector   <  string  >>     res  ;             // Maps hash to index in result      unordered_map   <  string       int  >     mp  ;             for     (  string     s     :     arr  )     {         // Generate hash representing the shift pattern      string     hash     =     getHash  (  s  );             // If new hash create a new group      if     (  mp  .  find  (  hash  )     ==     mp  .  end  ())     {         mp  [  hash  ]     =     res  .  size  ();         res  .  push_back  ({});      }      // Add string to its group      res  [  mp  [  hash  ]].  push_back  (  s  );         }      return     res  ;   }   int     main  ()     {      vector   <  string  >     arr     =     {  'acd'       'dfg'       'wyz'       'yab'       'mop'       'bdfh'       'a'       'x'       'moqs'  };      vector   <  vector   <  string  >>     groups     =     groupShiftedString  (  arr  );          for     (  vector   <  string  >     &  group     :     groups  )     {      for     (  string     &  s     :     group  )     {      cout      < <     s      < <     ' '  ;      }      cout      < <     endl  ;      }      return     0  ;   }   
Java
   // Java program to print groups of shifted strings   // together using Hash Map   import     java.util.*  ;   class   GfG     {      // Function to generate hash by shifting and equating the      // first character      static     String     getHash  (  String     s  )     {          // Calculate the shift needed to normalize the string      int     shifts     =     s  .  charAt  (  0  )     -     'a'  ;         char  []     chars     =     s  .  toCharArray  ();          for     (  int     i     =     0  ;     i      <     chars  .  length  ;     i  ++  )     {          // Adjust each character by the shift      chars  [  i  ]     =     (  char  )     (  chars  [  i  ]     -     shifts  );             // Wrap around if the character goes below 'a'      if     (  chars  [  i  ]      <     'a'  )         chars  [  i  ]     +=     26  ;         }      return     new     String  (  chars  );      }      // Function to group shifted strings together      static     ArrayList   <  ArrayList   <  String  >>     groupShiftedString  (  String  []     arr  )     {      ArrayList   <  ArrayList   <  String  >>     res     =     new     ArrayList   <>  ();          // Maps hash to index in result      HashMap   <  String       Integer  >     mp     =     new     HashMap   <>  ();         for     (  String     s     :     arr  )     {          // Generate hash representing the shift pattern      String     hash     =     getHash  (  s  );         // If new hash create a new group      if     (  !  mp  .  containsKey  (  hash  ))     {      mp  .  put  (  hash       res  .  size  ());      res  .  add  (  new     ArrayList   <>  ());      }      // Add string to its group      res  .  get  (  mp  .  get  (  hash  )).  add  (  s  );         }      return     res  ;      }      public     static     void     main  (  String  []     args  )     {      String  []     arr     =     {  'acd'       'dfg'       'wyz'       'yab'       'mop'       'bdfh'       'a'       'x'       'moqs'  };      ArrayList   <  ArrayList   <  String  >>     groups     =     groupShiftedString  (  arr  );      for     (  ArrayList   <  String  >     group     :     groups  )     {      for     (  String     s     :     group  )     {      System  .  out  .  print  (  s     +     ' '  );      }      System  .  out  .  println  ();      }      }   }   
Python
   # Python program to print groups of shifted strings   # together using Hash Map   # Function to generate hash by shifting and equating the first character   def   getHash  (  s  ):   # Calculate the shift needed to normalize the string   shifts   =   ord  (  s  [  0  ])   -   ord  (  'a'  )   hashVal   =   []   for   ch   in   s  :   # Adjust each character by the shift   newCh   =   chr  (  ord  (  ch  )   -   shifts  )   # Wrap around if the character goes below 'a'   if   newCh    <   'a'  :   newCh   =   chr  (  ord  (  newCh  )   +   26  )   hashVal  .  append  (  newCh  )   return   ''  .  join  (  hashVal  )   # Function to group shifted strings together   def   groupShiftedString  (  arr  ):   res   =   []   # Maps hash to index in result   mp   =   {}   for   s   in   arr  :   # Generate hash representing the shift pattern   hashVal   =   getHash  (  s  )   # If new hash create a new group   if   hashVal   not   in   mp  :   mp  [  hashVal  ]   =   len  (  res  )   res  .  append  ([])   # Add string to its group   res  [  mp  [  hashVal  ]]  .  append  (  s  )   return   res   if   __name__   ==   '__main__'  :   arr   =   [  'acd'     'dfg'     'wyz'     'yab'     'mop'     'bdfh'     'a'     'x'     'moqs'  ]   groups   =   groupShiftedString  (  arr  )   for   group   in   groups  :   print  (  ' '  .  join  (  group  ))   
C#
   // C# program to print groups of shifted strings   // together using Hash Map   using     System  ;   using     System.Collections.Generic  ;   class     GfG     {          // Function to generate hash by shifting and equating the first character      static     string     getHash  (  string     s  )     {      // Calculate the shift needed to normalize the string      int     shifts     =     s  [  0  ]     -     'a'  ;         char  []     chars     =     s  .  ToCharArray  ();          for     (  int     i     =     0  ;     i      <     chars  .  Length  ;     i  ++  )     {      // Adjust each character by the shift      chars  [  i  ]     =     (  char  )(  chars  [  i  ]     -     shifts  );             // Wrap around if the character goes below 'a'      if     (  chars  [  i  ]      <     'a'  )         chars  [  i  ]     +=     (  char  )  26  ;         }      return     new     string  (  chars  );      }      // Function to group shifted strings together      static     List   <  List   <  string  >>     groupShiftedString  (  string  []     arr  )     {      List   <  List   <  string  >>     res     =     new     List   <  List   <  string  >>  ();          // Maps hash to index in result      Dictionary   <  string       int  >     mp     =     new     Dictionary   <  string       int  >  ();         foreach     (  string     s     in     arr  )     {      // Generate hash representing the shift pattern      string     hash     =     getHash  (  s  );         // If new hash create a new group      if     (  !  mp  .  ContainsKey  (  hash  ))     {         mp  [  hash  ]     =     res  .  Count  ;      res  .  Add  (  new     List   <  string  >  ());      }      // Add string to its group      res  [  mp  [  hash  ]].  Add  (  s  );         }      return     res  ;      }      static     void     Main  (  string  []     args  )     {      string  []     arr     =     {     'acd'       'dfg'       'wyz'       'yab'       'mop'       'bdfh'       'a'       'x'       'moqs'     };      var     groups     =     groupShiftedString  (  arr  );      foreach     (  var     group     in     groups  )     {      Console  .  WriteLine  (  string  .  Join  (  ' '       group  ));      }      }   }   
JavaScript
   // JavaScript program to print groups of shifted strings   // together using Hash Map   // Function to generate hash by shifting and equating the first character   function     getHash  (  s  )     {          // Calculate the shift needed to normalize the string      const     shifts     =     s  .  charCodeAt  (  0  )     -     'a'  .  charCodeAt  (  0  );             let     chars     =     [];      for     (  let     ch     of     s  )     {      // Adjust each character by the shift      let     newChar     =     String  .  fromCharCode  (  ch  .  charCodeAt  (  0  )     -     shifts  );          // Wrap around if the character goes below 'a'      if     (  newChar      <     'a'  )         newChar     =     String  .  fromCharCode  (  newChar  .  charCodeAt  (  0  )     +     26  );         chars  .  push  (  newChar  );      }          return     chars  .  join  (  ''  );   }   // Function to group shifted strings together   function     groupShiftedString  (  arr  )     {      const     res     =     [];             // Maps hash to index in result      const     mp     =     new     Map  ();         for     (  let     s     of     arr  )     {      // Generate hash representing the shift pattern      const     hash     =     getHash  (  s  );         // If new hash create a new group      if     (  !  mp  .  has  (  hash  ))     {         mp  .  set  (  hash       res  .  length  );      res  .  push  ([]);      }      // Add string to its group      res  [  mp  .  get  (  hash  )].  push  (  s  );         }      return     res  ;   }   // Driver Code   const     arr     =     [  'acd'       'dfg'       'wyz'       'yab'       'mop'       'bdfh'       'a'       'x'       'moqs'  ];   const     groups     =     groupShiftedString  (  arr  );   groups  .  forEach  (  group     =>     console  .  log  (  group  .  join  (  ' '  )));   

Wyjście
acd dfg wyz yab mop bdfh moqs a x  

Złożoność czasowa: O(n*k) gdzie n jest długością tablicy ciągów, a k jest maksymalną długością ciągu w tablicy ciągów.
Przestrzeń pomocnicza: O(n*k) w najgorszym przypadku możemy wygenerować odpowiednio n różnych ciągów skrótu dla każdego ciągu wejściowego. Mamy więc n różnych wpisów na mapie skrótów, każdy o długości k lub mniejszej.