
Data Structure
Networking
RDBMS
Operating System
Java
MS Excel
iOS
HTML
CSS
Android
Python
C Programming
C++
C#
MongoDB
MySQL
Javascript
PHP
- Selected Reading
- UPSC IAS Exams Notes
- Developer's Best Practices
- Questions and Answers
- Effective Resume Writing
- HR Interview Questions
- Computer Glossary
- Who is Who
Similar String Groups in C++
Suppose we have two strings X and Y, these are similar if we can swap two letters of X, so that it equals Y. Also two the strings X and Y are similar if they are equal. As an example, consider, two strings are like "tars" and "rats" are similar, if we swap t and r, then we can find another, now "rats" and "arts" are similar, but "star" is not similar to "tars", "rats", or "arts". Now we can see, these form two connected groups by similarity: {"tars", "rats", "arts"} and {"star"}. Here "tars" and "arts" are in the same group even though they are not similar. So, each group is such that a word is in the group if and only if it is similar to at least one other word in the group. Suppose we have a list A of strings. Every string in A is an anagram of every other string in A. We have to find how many groups are there?
So, if the input is like ["tars","rats","arts","star"], then the output will be 2
To solve this, we will follow these steps −
Define an array parent
Define an array rank
-
Define a function getParent(), this will take x,
-
if parent[x] is same as -1, then −
return x
return parent[x] = getParent(parent[x])
-
-
Define a function unionn(), this will take x, y,
parX := getParent(x), parY := getParent(y)
-
if parX is same as parY, then −
return false
-
if rank[parX] >= rank[parY], then −
rank[parX] := rank[parX] + rank[parY]
parent[parY] := parX
-
Otherwise
rank[parY] := rank[parY] + rank[parX]
parent[parX] := parY
return true
-
Define a function ok(), this will take s1, s2,
cnt := 0
-
for initialize i := 0, when i < size of s1, update (increase i by 1), do −
-
if s1[i] is not equal to s2[i], then −
(increase cnt by 1)
-
if cnt > 2, then −
return false
-
return true
From the main method, do the following −
ret := 0
n := size of A
ret := n
parent := an array of size n, and fill this with -1
rank := an array of size n, and fill this with 1
-
for initialize i := 0, when i < n, update (increase i by 1), do −
-
for initialize j := i + 1, when j < n, update (increase j by 1), do −
-
if ok(A[i], A[j]) is non-zero, then −
-
if unionn(i, j) is non-zero, then −
(decrease ret by 1)
-
-
-
return ret
Let us see the following implementation to get better understanding −
Example
#include <bits/stdc++.h> using namespace std; void print_vector(vector<auto> v){ cout << "["; for(int i = 0; i<v.size(); i++){ cout << v[i] << ", "; } cout << "]"<<endl; } class Solution { public: vector<int> parent; vector<int> rank; int getParent(int x){ if (parent[x] == -1) return x; return parent[x] = getParent(parent[x]); } bool unionn(int x, int y){ int parX = getParent(x); int parY = getParent(y); if (parX == parY) return false; if (rank[parX] >= rank[parY]) { rank[parX] += rank[parY]; parent[parY] = parX; } else { rank[parY] += rank[parX]; parent[parX] = parY; } return true; } bool ok(string& s1, string& s2){ int cnt = 0; for (int i = 0; i < s1.size(); i++) { if (s1[i] != s2[i]) cnt++; if (cnt > 2) return false; } return true; } int numSimilarGroups(vector<string>& A){ int ret = 0; int n = A.size(); ret = n; parent = vector<int>(n, -1); rank = vector<int>(n, 1); for (int i = 0; i < n; i++) { for (int j = i + 1; j < n; j++) { if (ok(A[i], A[j])) { if (unionn(i, j)) ret--; } } } return ret; } }; main(){ Solution ob; vector<string> v = {"tars","rats","arts","star"}; cout << (ob.numSimilarGroups(v)); }
Input
{"tars","rats","arts","star"}
Output
2