【LeetCode】Word Ladder

Given two words (start and end), and a dictionary, find the length of shortest transformation sequence from start to end, such that:

  1. Only one letter can be changed at a time
  2. 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",
return its length 5.

用BFS层序遍历,运用队列存储。遍历queue将每次改变一个位置字符的单词如果存在于下一层的queue中,则将其存于下一层队列中,并在dict中将此单词删除。

当此层queue为空时,遍历下一层queue,直到到达下列条件。

依次遍历,只到有一个单词改变一个字符等于end,则成功返回层数+1,如果最后dict为空还没找到这个单词则返回0.

 

开始时自己写的BFS,不能通过大集合。可能在于我每次都将字典里的单词遍历一遍,增加了时间复杂度导致的。

dict.length*str.length 当字典集合中的单词数过多时时间复杂会比较差。

public class Solution {
    public int ladderLength(String start, String end, HashSet<String> dict) {
        if(dict.isEmpty())
            return 0;
        if(start.equals(end))
            return 0;
        Queue<String> queue = new LinkedList<String>();
        Queue<String> tempqueue = new LinkedList<String>();
        HashSet<String> tempdict = new HashSet<String>();
        queue.add(start);
        int re =1;
        while(dict!=null&&!queue.isEmpty()){
            
                String sr = queue.peek();
                int recount = 0;
                int j=0;
      //寻找这一个单词是否能够改变一个字符位置就能达到end单词
while(j<sr.length()){ if(sr.charAt(j)!=end.charAt(j)) recount++; j++; } if(recount==1) return re+1; queue.poll(); Iterator<String> it = dict.iterator();
      //遍历dict,找到改变一个字符的单词
while(it.hasNext()){ String temp = it.next(); int count = 0; int i=0; while(i<sr.length()){ if(temp.charAt(i)!=sr.charAt(i)){ count++; } i++; } if(count==1){ tempqueue.offer(temp); }else{ tempdict.add(temp); } }
      //当这一层的queue为空时,重新遍历下一层,直到达到结束条件
if(queue.isEmpty()){ queue=tempqueue; tempqueue= new LinkedList<String>(); dict=tempdict; tempdict=new HashSet<String>(); re++; } } return 0; } }
在网上看到一种巧妙的方法,遍历24个字符,对单词中的一个位置的字符进行24中改变,从而达到了遍历的目的,这样循环次数不会超过 24*str.length
public class NSolution {
    public int ladderLength(String start, String end, HashSet<String> dict) {
        if(dict.isEmpty())
            return 0;
        if(start.equals(end))
            return 0;
        boolean bo = dict.contains("hot");
        Queue<String> queue = new LinkedList<String>();
        Queue<String> tempqueue = new LinkedList<String>();

        queue.add(start);
        int re =1;
        while(dict!=null&&!queue.isEmpty()){
            String str = queue.peek();
            char[] sr = str.toCharArray();
            queue.poll();
            int len = str.length();
            for(int i=0;i<len;i++){
                char temp = sr[i];
                for(char c ='a';c<='z';c++){
                    if(c==temp)
                        continue;
                    sr[i]=c;
                    String ns = String.valueOf(sr);
                    if(ns.equals(end))
                        return re+1;
                    if(dict.contains(ns)){
                        tempqueue.offer(ns);
                        dict.remove(ns);
                    }
                }
                sr[i]=temp;
            }
                
                if(queue.isEmpty()){
                    queue=tempqueue;
                    tempqueue= new LinkedList<String>();
                    
                    re++;
                }
    
        }
        return 0;
        
    }
}

 

 
posted @ 2014-05-14 20:21  一弦一仙  阅读(148)  评论(0)    收藏  举报