原题
Given an array of strings, group anagrams together.
Example:
Input: ["eat", "tea", "tan", "ate", "nat", "bat"],
Output:
[
["ate","eat","tea"],
["nat","tan"],
["bat"]
]
Note:
All inputs will be in lowercase.
The order of your output does not matter.
题目:
给定一个字符串数组, 将anagrams
组合在一起。(anagram的意思是:abc,bac,acb就是anagram。)
My Answer(超时)
思路分析
本题采用回溯算法。
- 基本思路是先排好序,这样做的目的是为了对数组后面不可能出现的情况进行排除,有利于减少查找时间,即剪枝操作
- 外层循环对数组元素依次进行遍历,依次将 nums 中的元素加入中间集,一旦满足条件,就将中间集加入结果集
- 然后每次递归中把剩下的元素一一加到结果集合中,并且把目标减去加入的元素,然后把剩下元素(包括当前加入的元素)放到下一层递归中解决子问题。
class Solution:
def groupAnagrams(self, strs):
"""
:type strs: List[str]
:rtype: List[List[str]]
"""
res = []
mark_index = []
for i in range(len(strs)):
if i in mark_index:
continue
else:
temp_list = []
temp_list.append(strs[i])
mark_index.append(i)
# del strs[i]
for j in range(i+1, len(strs)):
if len(strs[j]) != len(strs[i]):
continue
else:
if self.isrotate(strs[i], strs[j]):
temp_list.append(strs[j])
# del strs[j]
mark_index.append(j)
res.append(temp_list)
return res
def isrotate(self, model, temp):
temp_model = list(model)
temp_temp = list(temp)
temp_model.sort()
temp_temp.sort()
if temp_model == temp_temp:
return True
else:
return False
Reference Answer
思路分析
anagram的意思是:abc,bac,acb就是anagram。即同一段字符串的字母的不同排序。将这些都找出来。这里使用了哈希表,即Python中的dict。针对前面的例子来讲,映射为{abc:abc,bac,acb}。
class Solution:
def groupAnagrams(self, strs):
"""
:type strs: List[str]
:rtype: List[List[str]]
"""
temp_dict = {}
res = []
for i, count in enumerate(strs):
temp_sublist = "".join(sorted(count))
if temp_sublist not in temp_dict:
temp_dict[temp_sublist] = [count]
else:
temp_dict[temp_sublist].append(count)
for count in temp_dict.values():
res.append(count)
return res
反思:
- 首先,自己想到了一种尝试在遍历list时候,对list序列长度改变的一种折中方式(之前,自己一直尝试直接利用
del list[i]
删除,事实上这种做法是错误的,因为for i in range(len(strs)))
中的i
一旦开始,就会依据最初的(len(strs))
进行递增,不是每次都进行重新判定len(strs)
,所以后续遍历过程改变strs长度并不会影响i的取值范围,这也是直接del list[i]
容易引起outof the list index
错误原因),即记下要删除或者跳过的list元素索引为mark_index
,然后在遍历list时候,先进行判定i
是否在mark_index
中,这样就可以不对某些元素进行操作,直接跳过; - 注意:对字符串来说:
list(str)
不等于[str]
,如当str = 'abc'
时候,list(str) = ['a', 'b, 'c']
,而[str] = ['abc']
;这也是自己在写参考答案用list(count)
代替[count]
出错的原因; - sorted 函数的使用,自己之前只知道可以针对list用
list.sort()
,事实上sorted
用起来感觉比.sort()
还顺手一些,sorted
对列表、字符串都可使用,这在判断两字符串是否包含相同元素组成时候发挥了关键性作用; - 记住sorted 函数针对字符串的返回结果是以
list(str)
格式,如str = 'cba'
,则sorted(str) = ['a', 'b', 'c']
,所以,如果想恢复原格式,还需要list转str,操作为"".join(sorted(str))
- list也可用
+
操作,如['ab'] + [12]
的结果为['ab', 12]
; - 要记住取dict所有值的操作:
dict.values()
; - 判断两字符串是否包含相同字符时,不能简直直接通过判定某一字符串包含元素是否在另一字符串中进行判定,自己当时就直接判定为:
def isrotate(self, model, temp):
if temp[i] not in model:
return False
else:
pass
return True
这种操作就会出现当str1 = [‘abc’], str2 = [‘aba’]直接判定为相等,正确操作应该是直接判定两字符串经过排序后是否表现相同:
def isrotate(self, model, temp):
temp_model = list(model)
temp_temp = list(temp)
temp_model.sort()
temp_temp.sort()
if temp_model == temp_temp:
return True
else:
return False