题目
Given two words (start and end), and a dictionary, find all shortest transformation sequence(s) 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"]
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.
方法
算法思路和上一题基本上一致,只需要使用一个数据结构,来保存每一个结点的前驱结点。public List<List<String>> findLadders(String start, String end, Set<String> dict) { Queue<String> queue = new LinkedList<String>(); Map<String, Integer> map = new HashMap<String, Integer>(); Map<String, Set<String>> preSet = new HashMap<String, Set<String>>(); queue.offer(start); map.put(start, 1); int minLadder = dict.size() + 2; boolean flag = false; while (!queue.isEmpty()) { String str = queue.poll(); int count = map.get(str); if (count < minLadder) { for (int i = 0; i < str.length(); i++) { for (char k = 'a'; k <= 'z'; k++) { if (str.charAt(i) != k) { StringBuilder builder = new StringBuilder(str); builder.setCharAt(i, k); String temp = builder.toString(); if (temp.equals(end)) { if (preSet.containsKey(temp)) { preSet.get(temp).add(str); } else { Set<String> set = new HashSet<String>(); set.add(str); preSet.put(temp, set); } minLadder = count + 1; flag = true; } else if (dict.contains(temp)) { if (!map.containsKey(temp)) { queue.offer(temp); map.put(temp, count + 1); } if (map.get(temp) > map.get(str)) { if (preSet.containsKey(temp)) { preSet.get(temp).add(str); } else { Set<String> set = new HashSet<String>(); set.add(str); preSet.put(temp, set); } } } } } } } else { break; } } List<List<String>> list = new ArrayList<List<String>>(); if (flag) { List<String> subList = new ArrayList<String>(); subList.add(end); getList(preSet, end, subList, list); return list; } else { return list; } } private void getList(Map<String, Set<String>> preSet, String cur, List<String> subList, List<List<String>> list) { if (preSet.containsKey(cur)) { Set<String> set = preSet.get(cur); for (String str : set) { List<String> newList = new ArrayList<String>(subList); newList.add(str); getList(preSet, str, newList, list); } } else { Collections.reverse(subList); list.add(subList); } }