【Leetcode】49.字母異位分詞
阿新 • • 發佈:2020-12-14
題目連結
49. 字母異位詞分組
題目描述
解題思路
1.暴力法
兩個for迴圈,分別判斷兩個字串出現的字母個數是否相同,相同加入同一個List。時間複雜度基本等於O(n^2),Leetcode上提交是超時的。
2.hash法
對暴力法進行改進,利用List記錄字串出現的字母個數相同的字串,同時利用hash表記錄List在ans二維列表的下標,這樣只需要遍歷一遍陣列即可。
問題來了:hash表的值是下標,那hash表的鍵值該如何表示?
利用大小為26的陣列,並初始化值為-1,統計每個字母出現的次數,如果兩個字串符合要求,那麼兩個字串對應的陣列一定是相同的,所以由陣列值轉換成的字串也一定是相同的。所以hash表的鍵值為陣列值轉換成的字串
3.利用質數實現hash法
解法思路與2相同,首先為26個字元賦值為26個質數,因為質數與質數的乘積是唯一的,這符合hash表鍵值的要求。所以hash表的鍵值為對應字母的質數乘積。
AC程式碼
1.暴力法
class Solution { public int[] cal(String temp,int[] count){ for(int i = 0; i < temp.length(); i++){ count[temp.charAt(i)-'a']++; } return count; } public boolean test(int[] countA,int[] countB){ for(int i = 0; i < 26; i++){ if(countA[i] != countB[i]) return false; } return true; } public List<List<String>> groupAnagrams(String[] strs) { List<List<String>> ans = new LinkedList<>(); boolean flags[] = new boolean[strs.length]; for(int i = 0; i < strs.length; i++){ if(flags[i] == true) continue; List<String> temp = new LinkedList<>(); int countA[] = new int[26]; countA = cal(strs[i],countA); temp.add(strs[i]); for(int j = i + 1; j < strs.length; j++){ int countB[] = new int[26]; countB = cal(strs[j],countB); if(test(countA,countB)){ temp.add(strs[j]); flags[j] = true; } } ans.add(temp); } return ans; } }
2.hash表法
class Solution { public String count(String temp,int[] tot){ StringBuffer sb = new StringBuffer(); for(int i = 0; i < temp.length(); i++){ tot[temp.charAt(i)-'a']++; } for(int i = 0; i < tot.length; i++) sb.append(tot[i]); return sb.toString(); } public List<List<String>> groupAnagrams(String[] strs) { List<List<String>> ans = new LinkedList<>(); Map<String,Integer> hashTable = new HashMap<>(); for(int i = 0; i < strs.length; i++){ int[] countN = new int[26]; Arrays.fill(countN,-1); String str = count(strs[i],countN); if(hashTable.containsKey(str)){ int index = hashTable.get(str); ans.get(index).add(strs[i]); }else{ List<String> temp = new LinkedList<>(); temp.add(strs[i]); ans.add(temp); hashTable.put(str,ans.size()-1); } } return ans; } }
3.利用質數實現hash法
class Solution {
public:
vector<vector<string>> groupAnagrams(vector<string>& strs) {
vector<vector<string>> res;
unordered_map <double,vector<string> > m;
double a[26]={2,3,5,7,11,13,17,19,23,29,31,37,41,43,47,53,59,61,67,71,73,79,83,89,97,101};
for(string& s : strs)
{
double t = 1;
for(char c : s)
t *= a[c - 'a'];
m[t].push_back(s); //t為單詞對應的質數乘積,m[t]則為該單詞的異位詞構成的vector
}
for(auto& n : m) //n為鍵和值組成的pair
res.push_back(n.second);
return res;
}
};