p839. similar-string-groups
https://leetcode-cn.com/problems/similar-string-groups/
仍然是并查集,对于每一个当前遍历到的字符串,检查其后所有字符串是否和他相似。
这里采用从前向后判断而非从后向前判读,具体分析可知这样的比较次数要低于从后向前检查的比较次数。
c++代码:
#include <iostream>
#include <vector>
#include <string>
#include <cstring>
using namespace std;
class UFSets{
private:
int maxSize;
int setCount;//连通分量数
vector<int> parent;
public:
UFSets(int size=10):maxSize(size){
parent=vector<int>(size);
for(int i=0;i<size;i++){
parent[i]=-1;
}
setCount=size;
}
~UFSets(){
//delete parent;
}
int& operator[](int i){
return parent[i];
}
int Find(int v){
return parent[v]<0?v:Find(parent[v]);
};//查找v所在并查集的根
bool Union(int v1,int v2){
int r1=Find(v1),r2=Find(v2);
if(r1==r2){//若两个结点在同一个并查集
return false;
}
//不在一个并查集则合并
if(parent[r1]<=parent[r2]){
parent[r2]+=parent[r1];
parent[r1]=r2;
}
else{
parent[r1]+=parent[r2];
parent[r2]=r1;
}
setCount--;
return true;
};//将并查集r1和并查集r2合并
int size(){
return setCount;
}
};
bool isSim(const string& s1,const string &s2){
int size=s1.size();
int n=0;
for(int i=0;i<size;i++){
if(s1[i]!=s2[i]){
n++;
}
}
if(n<=2){
return true;
}
return false;
}
int numSimilarGroups(vector<string>& strs){
int size=strs.size();
if(size==0){
return 0;
}
UFSets set(size);
for(int i=0;i<size;i++){
for(int j=i+1;j<size;j++){
if(isSim(strs[i],strs[j])){
set.Union(i,j);
}
}
}
return set.size();
}
vector<string> split(string str,string del){
vector<string> ans;
char *s=new char[str.length()+1];
strcpy(s,str.c_str());
char *d=new char[del.length()];
strcpy(d,del.c_str());
char *p=strtok(s,d);
while(p){
ans.push_back(p);
p=strtok(NULL,d);
}
return ans;
}
int main(){
string s;
cin>>s;
vector<string> strs=split(s,",");
for(auto &s:strs){
s=s.substr(1,s.size()-1);
}
cout<<numSimilarGroups(strs)<<endl;
return 0;
}
输入格式:
"tars","rats","arts","star"
caution
输入处理部分:

浙公网安备 33010602011771号