链接:http://leetcode.com/onlinejudge#question_49
原题:
Given an array of strings, return all groups of strings that are anagrams.
Note: All inputs will be in lower-case.
思路:什么是anagram?一个字符串,把它的字母任意调换位置后,得到的字符串就叫原来的anagram,也就是原串的一个置换。
要把这些字符串全部找出来,我是自己实现了一个hashtable做的。key是该字符串的字母和,然后取余数。一旦发生冲突,就检查
是不是anagram。 最后是328ms跑过的。
在discussion里面,有另外比较简洁的做法,就是把每个string排序作为key,再用unordered_map,196ms跑过。
代码:
const int NUM = 26;
struct Node {
bool used;
string str;
vector<int> signature;
Node *next;
Node(): next(NULL) {}
Node(const string &s): used(false), str(s), next(NULL) {
signature.assign(NUM, 0);
for (int i=0; i<str.size(); i++)
signature[str[i]-'a']++;
}
};
class Solution {
public:
vector<string> anagrams(vector<string> &strs) {
// Start typing your C/C++ solution below
// DO NOT write int main() function
vector<string> collection;
freeSpace();
Node head;
hashTable.assign(SIZE, head);
for (int n=0; n<strs.size(); n++) {
int key = getKey(strs[n]);
if (hashTable[key].next == NULL) {
hashTable[key].next = new Node(strs[n]);
} else {
Node *cur = new Node(strs[n]);
Node *ptr = hashTable[key].next;
while (ptr) {
if (ptr->signature == cur->signature) {
collection.push_back(strs[n]);
if (ptr->used == false) {
collection.push_back(ptr->str);
ptr->used = true;
}
delete cur;
break;
}
ptr = ptr->next;
}
if (ptr == NULL) {
cur->next = hashTable[key].next;
hashTable[key].next = cur;
}
}
}
return collection;
}
private:
void freeSpace() {
for (int i=0; i<hashTable.size(); i++) {
Node * ptr = hashTable[i].next;
while (ptr) {
Node *pre = ptr->next;
delete ptr;
ptr = pre;
}
}
hashTable.clear();
}
int getKey(const string &str) {
int sum = 0;
for (int i=0; i<str.size(); i++)
sum += (str[i] - 'a');
return sum % SIZE;
}
const static int SIZE = 101;
vector<Node> hashTable;
};