127. Word Ladder

Given two words (beginWord and endWord), and a dictionary’s word list, find the length of shortest transformation sequence from beginWord to endWord, such that:

  1. Only one letter can be changed at a time.
  2. Each transformed word must exist in the word list. Note that beginWord is not a transformed word.

Note:

  1. Return 0 if there is no such transformation sequence.
  2. All words have the same length.
  3. All words contain only lowercase alphabetic characters.
  4. You may assume no duplicates in the word list.
  5. You may assume beginWord and endWord are non-empty and are not the same.

Example 1:

Input:

beginWord = "hit",
endWord = "cog",
wordList = ["hot","dot","dog","lot","log","cog"]

Output: 5

Explanation: As one shortest transformation is "hit" -> "hot" -> "dot" -> "dog" -> "cog",
return its length 5.

Example 2:

Input:
beginWord = "hit"
endWord = "cog"
wordList = ["hot","dot","dog","lot","log"]

Output: 0

Explanation: The endWord "cog" is not in wordList, therefore no possible transformation.

方法1: bfs

思路:

从beginWord开始,每次尝试将某个位置上的字母变成’a’ - 'z’中的一个,这些变化中,有哪些是在dictionary里面的,我们就有可能在该单词的基础上继续变化,向下搜索。此时要注意几点:

  1. 每次变化都要记录一个和始发点的距离,而第一次找到endword的单词,一定是距离最短的。这也是bfs的特点。
  2. 因此,我们需要将每次遇到的单词从dictionary中去掉遇到过的单词:第一是因为,没有必要再保留这个单词,下一次遇到时所经过的变化次数,一定更多。第二是因为,如果保留,会出现相邻两层之间死循环的情况。第三,自己和自己之间就会出现死循环。

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

Complexity

Time complexity: O(n ^26len),


class Solution {
public:
    int ladderLength(string beginWord, string endWord, vector<string>& wordList) {
        set<string> wordSet(wordList.begin(), wordList.end());
        if (wordSet.empty() || !wordSet.count(endWord)) return 0;
        
        queue<string> q;
        q.push(beginWord);
        int level = 1;
        while (!q.empty()) {
            int size = q.size();
            for (int i = 0; i < size; i++) {
                string top = q.front();
                q.pop();
                
                for (int j = 0; j < top.size(); j++) {
                    for (char change = 'a'; change < 'z'; change++) {
                        string next = top;
                        next[j] = change;
                        
                        if (next == endWord) return level + 1;
                        
                        if (wordSet.count(next)) {
                            q.push(next);
                            wordSet.erase(next);
                        }
                    }
                }
            }
            level++;
        }
        return 0;
    }
};

方法2: bidirectional bfs

huahua: https://zxi.mytechroad.com/blog/searching/127-word-ladder/

思路:

Complexity

Time complexity: O(n ^26len/2),

class Solution {
public:
    int ladderLength(string beginWord, string endWord, vector<string>& wordList) {
        set<string> wordSet(wordList.begin(), wordList.end());
        if (!wordSet.count(endWord)) return 0;
        
        queue<string> q1, q2;
        unordered_map<string, int> visited1, visited2;
        q1.push(beginWord);
        q2.push(endWord);
        visited1.insert({beginWord, 1});
        visited2.insert({endWord, 1});
        int level1 = 1, level2 = 1;
        while (!q1.empty() && !q2.empty()) {
            int size1 = q1.size();
            for (int i = 0; i < size1; i++) {
                string top = q1.front();
                q1.pop();
                
                for (int j = 0; j < top.size(); j++) {
                    for (char change = 'a'; change < 'z'; change++) {
                        string next = top;
                        next[j] = change;
                        
                        if (visited2.count(next)) return level1 + visited2[next];
                        
                        if (wordSet.count(next)) {
                            visited1.insert({next, level1 + 1});
                            q1.push(next);
                            wordSet.erase(next);
                        }
                    }
                }
            }
            level1++;
            
            
            int size2 = q2.size();
            for (int i = 0; i < size2; i++) {
                string top = q2.front();
                q2.pop();
                
                for (int j = 0; j < top.size(); j++) {
                    for (char change = 'a'; change < 'z'; change++) {
                        string next = top;
                        next[j] = change;
                        
                        if (visited1.count(next)) return level2 + visited1[next];
                        
                        if (wordSet.count(next)) {
                            visited2.insert({next, level2 + 1});
                            q2.push(next);
                            wordSet.erase(next);
                        }
                    }
                }
            }
            level2++;
        }
        return 0;
    }
};
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值