Given an array of strings, group anagrams together.
For example, given: ["eat", "tea", "tan", "ate", "nat", "bat"]
,
Return:
[ ["ate", "eat","tea"], ["nat","tan"], ["bat"] ]
Note:
- For the return value, each inner list's elements must follow the lexicographic order.
- All inputs will be in lower-case.
Solution:
1. To determine if one is anagram of another, we can sort both and compare if their sorted outputs are the same.
2. To keep track if a string belongs to a group, ew use a hash map. If the sorted string is found in the map, then it belongs to a group. The value of the map can be the number of the group the string belongs to.
2. The maintain order, we first sort the original input. In this way we scan through strings with lexical order. And strings would be pushed into final result in lexical order.
Code:
class Solution {
public:
vector<vector<string>> groupAnagrams(vector<string>& strs) {
map<string, int> mapp;
vector<int> group_ind(strs.size());
sort(strs.begin(), strs.end());//maintain order in output
int group_count = 0;//counting how many groups
for(int i = 0; i < strs.size(); i++){
string s = strs[i];
sort(s.begin(), s.end());//sort the string
if(mapp.find(s)==mapp.end()){//if the string could not be found, create a new group
mapp[s] = group_count;//note the group number for the set of this string
group_ind[i] = group_count;//note the group number for current string
group_count++;
}
else
group_ind[i] = mapp[s];//note the group number for current string
}
vector<vector<string>> res(group_count);
for(int i = 0; i < strs.size(); i ++){
res[group_ind[i]].push_back(strs[i]);
}
return res;
}
};