LeetCode Daily Question839。同様の文字列グループ

839.同様の文字列グループ

文字列Xなど、2つの異なる位置にある文字の交換文字Yが等しい場合、いわゆるX、とY2つの類似した文字列。2つの文字列自体が等しい場合、それらも類似しています。

たとえば、"tars"および"rats"類似(交換0および2位置);"rats"および"arts"類似しているが、"star"そうではない"tars""rats"または"arts"類似。

要するに、それらは類似性を通じて2つの関連グループを形成{"tars", "rats", "arts"}{"star"}ます"tars""arts"は、類似していなくても同じグループに属していることに注意してください正式には、各グループについて、グループ内の単語を決定するために、それはグループ内の少なくとも1つの単語に類似している必要があるだけです。

文字列のリストを提供しますstrs各文字列は、strs異所性のすべての文字列という単語の他の文字のリストですstrs同様のグループの文字列をどれだけ尋ねますか?

例1:

输入:strs = ["tars","rats","arts","star"]
输出:2

例2:

输入:strs = ["omv","ovm"]
输出:1

促す:

  • 1 <= strs.length <= 100
  • 1 <= strs [i] .length <= 1000
  • sum(strs [i] .length)<= 2 * 104
  • strs [i]には小文字のみが含まれます。
  • strsのすべての単語は同じ長さであり、互いに透けて見える単語です。

備考:

  • アナグラムは、文字列の文字の位置(順序)を変更することによって形成される新しい単語です。

方法1:収集して確認する

問題解決のアイデア

もちろん、1月の最終日は「コンバインドチェックコレクション」で終わる必要があります〜

特別な解決策はありません。2層ループは、2つの文字列が「類似した文字列」であるかどうかを正直に比較します。文字列がunion一緒に缶にている場合

参照コード

public int numSimilarGroups(String[] strs) {
    
    
    int n = strs.length;
    UnionFind unionFind = new UnionFind(n);
    for (int i = 0; i < n - 1; i++) {
    
    
        for (int j = i + 1; j < n; j++) {
    
    
            if (unionFind.connected(i, j)) {
    
    
                continue;
            }
            if (isSimilar(strs[i], strs[j])) {
    
    
                unionFind.union(i, j);
            }
        }
    }
    return unionFind.getCount();
}
// 判断两个字符串是否为“相似字符串”
public boolean isSimilar(String s1, String s2) {
    
    
    char[] cs1 = s1.toCharArray(), cs2 = s2.toCharArray();
    int num = 0;
    for (int i = 0; i < cs1.length; i++) {
    
    
        if (cs1[i] != cs2[i]) {
    
    
            num++;
            if (num > 2) {
    
    
                return false;
            }
        }
    }
    return true;
}
// 并查集模板
class UnionFind {
    
    
    private int[] parent;
    private int count;

    public UnionFind(int n) {
    
    
        count = n;
        parent = new int[n];
        for (int i = 0; i < n; i++) {
    
    
            parent[i] = i;
        }
    }

    public void union(int x, int y) {
    
    
        int rootX = find(x), rootY = find(y);
        if (rootX == rootY) {
    
    
            return;
        }
        parent[rootX] = rootY;
        count--;
    }

    public int find(int x) {
    
    
        return parent[x] == x ? parent[x] : (parent[x] = find(parent[x]));
    }

    public boolean connected(int x, int y) {
    
    
        return find(x) == find(y);
    }

    public int getCount() {
    
    
        return count;
    }
}

の結果
ここに画像の説明を挿入

おすすめ

転載: blog.csdn.net/qq_27007509/article/details/113470700