Given two words (start and end), and a dictionary, find the length of shortest transformation sequence from start to end, such that:
- Only one letter can be changed at a time
- Each intermediate word must exist in the dictionary
For example,
Given:
start ="hit"
end = "cog"
dict = ["hot","dot","dog","lot","log"]
As one shortest transformation is "hit" -> "hot" -> "dot" -> "dog" -> "cog"
,
5
. Note:
-
- Return 0 if there is no such transformation sequence.
- All words have the same length.
- All words contain only lowercase alphabetic characters.
乍看起来很难的一题,其实仔细分析就是图的遍历。把start,end和dict里的词都看作一个个结点,如果一个词可以合法转化为另一个词,那么视为这两个“结点”中间有一条路径。问题则变为,找到从start到end的最短路径长度。
如果采用扫描所有dict中单词,然后判断是否合法来遍历结点的方法,会超时(因为有dict中单词过多的用例)。所以只能采用别的遍历思路。
一个有效的遍历思路是获取到当前单词长度,然后对每一位都尝试替换为别的字符来遍历,即得到所以可能的合法字符串,然后判断是否等于end,或者在dict中且不在已遍历过的结点中,这样时间复杂度就是O(l)仅仅跟单词长度有关了。
对每一个结点,都用HashMap保存start到它的路径长度,新结点进入时只需要把长度加一即可。
采用广度优先遍历比较好,因为我们只需要获得最短的路径长度,而广度优先可以保证第一个到达end的路径是最短的(即到达end即可以return)。
代码如下:
1 public int ladderLength(String start, String end, Setdict) { 2 HashMap hm = new HashMap (); 3 Queue q = new LinkedList (); 4 q.add(start); 5 hm.put(start,1); 6 7 while(!q.isEmpty()) 8 { 9 String temp = q.poll();10 int len = hm.get(temp);11 for(int i=0;i