leetcode49. 字母异位词分组

法一:每个字符串先排序,再加入到HashMap。自己写的。
class Solution {
public List<List<String>> groupAnagrams(String[] strs) {
int n = strs.length;
HashMap<String,List<String>> mapStr = new HashMap<>();
for(int i = 0;i < n;++i){
char[] charArray = strs[i].toCharArray();// 1. 将字符串转换为字符数组
Arrays.sort(charArray);// 2. 对字符数组进行排序
String sortedStr = new String(charArray);// 3. 将排序后的字符数组转换回字符串
if(!mapStr.containsKey(sortedStr)){
List<String> strList = new ArrayList<>();
strList.add(strs[i]);
mapStr.put(sortedStr,strList);
}else{
mapStr.get(sortedStr).add(strs[i]);
}
}
return new ArrayList<>(mapStr.values());
}
}
法一优化:使用 getOrDefault()或 computeIfAbsent()简化代码
class Solution {
public List<List<String>> groupAnagrams(String[] strs) {
HashMap<String, List<String>> mapStr = new HashMap<>();
for (String str : strs) {
char[] charArray = str.toCharArray();
Arrays.sort(charArray);
String sortedStr = new String(charArray);
// 使用 computeIfAbsent 简化代码
mapStr.computeIfAbsent(sortedStr, k -> new ArrayList<>()).add(str);
}
return new ArrayList<>(mapStr.values());
}
}
class Solution {
public List<List<String>> groupAnagrams(String[] strs) {
return new ArrayList<>(
Arrays.stream(strs)
.collect(Collectors.groupingBy(s -> {
char[] sortedS = s.toCharArray();
Arrays.sort(sortedS);
return new String(sortedS);
}))
.values()
);
}
}
法二:考虑使用字符计数法避免排序
假设我们有以下几个字符串,来看看它们生成的 key:
| 原始字符串 | 字符计数数组(简化表示) | 生成的键 (key) |
|---|---|---|
""(空字符串) |
所有字母计数均为0 | #0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0 |
"a" |
a=1, 其余为0 | #1#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0 |
"cab" |
a=1, b=1, c=1, 其余为0 | #1#1#1#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0#0 |
"eat" |
a=1, e=1, t=1, 其余为0 | #1#0#0#0#1#0#0#0#0#0#0#0#0#0#0#0#0#0#0#1#0#0#0#0#0#0 |
class Solution {
public List<List<String>> groupAnagrams(String[] strs) {
Map<String, List<String>> map = new HashMap<>();
for (String str : strs) {
int[] count = new int[26];
for (char c : str.toCharArray()) {
count[c - 'a']++;
}
// 构建计数键,添加分隔符避免歧义[2](@ref)
StringBuilder keyBuilder = new StringBuilder();
for (int i = 0; i < 26; i++) {
keyBuilder.append('#').append(count[i]);
}
String key = keyBuilder.toString();
map.computeIfAbsent(key, k -> new ArrayList<>()).add(str);
}
return new ArrayList<>(map.values());
}
}
法三:质数乘积法(数学方法)
为每个字母分配一个质数,通过质数乘积的唯一性作为键
可能溢出,需要处理大数情况
class Solution {
public List<List<String>> groupAnagrams(String[] strs) {
int[] primes = {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};
Map<Long, List<String>> map = new HashMap<>();
for (String str : strs) {
long product = 1;
for (char c : str.toCharArray()) {
product *= primes[c - 'a'];
}
map.computeIfAbsent(product, k -> new ArrayList<>()).add(str);
}
return new ArrayList<>(map.values());
}
}
浙公网安备 33010602011771号