• [leetcode] Word Ladder2


    题目

    Given two words (start and end), and a dictionary, find all shortest transformation sequence(s) 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"]

    Return

      [
        ["hit","hot","dot","dog","cog"],
        ["hit","hot","lot","log","cog"]
      ]

    Note:

    • All words have the same length.
    • All words contain only lowercase alphabetic characters.

    题解

    答案是http://www.1point3acres.com/bbs/thread-51646-1-1.html 上面 iostreamin写的。

    我就直接贴过来就好,这道题多读读代码看明白。

     代码:

    复制代码
      1    public ArrayList<ArrayList<String>> findLadders(String start, String end, HashSet<String> dict) {  
      2           
      3         HashMap<String, HashSet<String>> neighbours = new HashMap<String, HashSet<String>>();  
      4           
      5         dict.add(start);  
      6         dict.add(end);  
      7           
      8         // init adjacent graph          
      9         for(String str : dict){  
     10             calcNeighbours(neighbours, str, dict);  
     11         }  
     12           
     13         ArrayList<ArrayList<String>> result = new ArrayList<ArrayList<String>>();  
     14           
     15         // BFS search queue  
     16         LinkedList<Node> queue = new LinkedList<Node>();  
     17         queue.add(new Node(null, start, 1)); //the root has not parent and its level == 1 
     18           
     19         // BFS level  
     20         int previousLevel = 0;  
     21           
     22         // mark which nodes have been visited, to break infinite loop  
     23         HashMap<String, Integer> visited = new HashMap<String, Integer>();   
     24         while(!queue.isEmpty()){  
     25             Node n = queue.pollFirst();              
     26             if(end.equals(n.str)){   
     27                 // fine one path, check its length, if longer than previous path it's valid  
     28                 // otherwise all possible short path have been found, should stop  
     29                 if(previousLevel == 0 || n.level == previousLevel){  
     30                     previousLevel = n.level;  
     31                     findPath(n, result);                      
     32                 }else {  
     33                     // all path with length *previousLevel* have been found  
     34                     break;  
     35                 }                  
     36             }else {  
     37                 HashSet<String> set = neighbours.get(n.str);                   
     38                   
     39                 if(set == null || set.isEmpty()) continue;  
     40                 // note: I'm not using simple for(String s: set) here. This is to avoid hashset's  
     41                 // current modification exception.  
     42                 ArrayList<String> toRemove = new ArrayList<String>();  
     43                 for (String s : set) {  
     44                       
     45                     // if s has been visited before at a smaller level, there is already a shorter   
     46                     // path from start to s thus we should ignore s so as to break infinite loop; if   
     47                     // on the same level, we still need to put it into queue.  
     48                     if(visited.containsKey(s)){  
     49                         Integer occurLevel = visited.get(s);  
     50                         if(n.level+1 > occurLevel){  
     51                             neighbours.get(s).remove(n.str);  
     52                             toRemove.add(s);  
     53                             continue;  
     54                         }  
     55                     }  
     56                     visited.put(s,  n.level+1);  
     57                     queue.add(new Node(n, s, n.level + 1));  
     58                     if(neighbours.containsKey(s))  
     59                         neighbours.get(s).remove(n.str);  
     60                 }  
     61                 for(String s: toRemove){  
     62                     set.remove(s);  
     63                 }  
     64             }  
     65         }  
     66   
     67         return result;  
     68     }  
     69       
     70     public void findPath(Node n, ArrayList<ArrayList<String>> result){  
     71         ArrayList<String> path = new ArrayList<String>();  
     72         Node p = n;  
     73         while(p != null){  
     74             path.add(0, p.str);  
     75             p = p.parent;   
     76         }  
     77         result.add(path);  
     78     }  
     79   
     80     /* 
     81      * complexity: O(26*str.length*dict.size)=O(L*N) 
     82      */  
     83     void calcNeighbours(HashMap<String, HashSet<String>> neighbours, String str, HashSet<String> dict) {  
     84         int length = str.length();  
     85         char [] chars = str.toCharArray();  
     86         for (int i = 0; i < length; i++) {  
     87               
     88             char old = chars[i];   
     89             for (char c = 'a'; c <= 'z'; c++) {  
     90   
     91                 if (c == old)  continue;  
     92                 chars[i] = c;  
     93                 String newstr = new String(chars);                  
     94                   
     95                 if (dict.contains(newstr)) {  
     96                     HashSet<String> set = neighbours.get(str);  
     97                     if (set != null) {  
     98                         set.add(newstr);  
     99                     } else {  
    100                         HashSet<String> newset = new HashSet<String>();  
    101                         newset.add(newstr);  
    102                         neighbours.put(str, newset);  
    103                     }  
    104                 }                  
    105             }  
    106             chars[i] = old;  
    107         }  
    108     }  
    109       
    110     private class Node {  
    111         public Node parent;  //previous node
    112         public String str;  
    113         public int level;  
    114         public Node(Node p, String s, int l){  
    115             parent = p;  
    116             str = s;  
    117             level = l;  
    118         }  
    119     } 
    复制代码
  • 相关阅读:
    maven项目从本地向本地仓库导入jar包
    身份证图片信息获取
    使用阿里云短信服务发送短信验证码
    网上爬取快递100的快递公司名称和公司编码
    快递100通过快递单号实时查询物流信息
    @autowired注入静态变量
    MySql多机优化---读写分离流程分析
    MySQL单机优化---SQL优化
    MySQL单机优化---分表、分区、分库
    MySQL数据库优化
  • 原文地址:https://www.cnblogs.com/fengmangZoo/p/4197070.html
Copyright © 2020-2023  润新知