forked from 7oSkaaa/LeetCode_DailyChallenge_2023
-
Notifications
You must be signed in to change notification settings - Fork 1
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
2be1c02
commit 051590d
Showing
1 changed file
with
76 additions
and
0 deletions.
There are no files selected for viewing
76 changes: 76 additions & 0 deletions
76
04- April/28- Similar String Groups/28- Similar String Groups (Ahmed Gamal).js
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,76 @@ | ||
// Author: Ahmed Gamal | ||
|
||
// for this problem, we can represent the relations between the strings as a graph, where each node is a string (refrenced by its index in the array) and each edge is a relation between two strings (if they are similar or not) | ||
// so we can use the disjoint set union (DSU) data structure to solve this problem, where each node will be represented by its index in the array and each node will have a parent node (initially each node is its own parent) | ||
// and we will loop over the array of strings and for each string we will loop over the rest of the strings and check if they are similar or not, if they are similar and they are not in the same group (they have different parents) then we will join them in the same group (make the parent of the first string the parent of the second string) | ||
// and the answer will be the number of groups in the DSU data structure | ||
|
||
/** | ||
* @param {string[]} strs | ||
* @return {number} | ||
*/ | ||
|
||
// DSU data structure | ||
class DSU { | ||
constructor(n) { | ||
this.p = Array(n).fill(0); | ||
this.rank = Array(n).fill(0); | ||
|
||
for(let i = 0; i < n; i++) { | ||
this.p[i] = i; | ||
} | ||
} | ||
|
||
get(x) { | ||
this.p[x] = x == this.p[x] ? x : this.get(this.p[x]); | ||
return this.p[x]; | ||
} | ||
|
||
join(u, v) { | ||
u = this.get(u), v = this.get(v); | ||
|
||
if(u == v) { | ||
return; | ||
} | ||
|
||
if(this.rank[u] === this.rank[v]) { | ||
this.rank[u]++; | ||
} | ||
|
||
if(this.rank[u] > this.rank[v]) { | ||
this.p[v] = u; | ||
} else { | ||
this.p[u] = v; | ||
} | ||
} | ||
} | ||
|
||
var numSimilarGroups = function(strs) { | ||
let n = strs.length; | ||
let d = new DSU(n); | ||
|
||
// initially each string is in its own group | ||
let ans = n; | ||
for(let i = 0; i < n; i++) { | ||
// m: length of the current string | ||
let m = strs[i].length; | ||
for(let j = i + 1; j < n; j++) { | ||
// cnt: number of different characters between the two strings | ||
let cnt = 0; | ||
for(let k = 0; k < m; k++) { | ||
// if the two strings are similar, then they will have at most 2 different characters | ||
cnt += strs[i][k] !== strs[j][k] ? 1 : 0; | ||
} | ||
|
||
// if the two strings are similar and they are not in the same group, then join them in the same group | ||
if((cnt === 0 || cnt === 2) && d.get(i) !== d.get(j)) { | ||
// decrease the number of groups by 1 | ||
ans--; | ||
d.join(i, j); | ||
} | ||
} | ||
} | ||
|
||
// return the number of groups | ||
return ans; | ||
}; |