[leetcode] Word Ladder

本文将问题抽象为图模型,通过宽度优先搜索(BFS)算法寻找从起点到终点的最短路径,实现单词接龙游戏的解题过程。

Word Ladder

把本题抽象为图模型:节点为length(length为start的长度)位个字母(每个字母有26种可能)的排列组合;若一个节点A通过改变一个字母变化到另外一个节点B(B节点在dict中),则有一条边A--B;否则两节点间没有边。此题可抽象为已知起点和终点,是否可以找到一条最短路径L,使得通过L,可以从起点到达终点。可以使用BFS来解。

#include <iostream>
#include <unordered_set>//mac os下引用unordered_set,散列容器
#include <string>
#include <queue>
using namespace std;

class Solution {
public:
    int ladderLength(string start, string end, unordered_set<string> &dict) {
        
        if (start==end) {
            return 1;
        }
        
        queue<string> nodes;//使用queue容器
        queue<int> depth;
        
        nodes.push(start);//start入队列
        depth.push(1);//1入队
        
        findItem(start, dict);//查看是否存在于字典中
        
        while (nodes.size()>0) {//遍历每一个单词
            
            string cur=nodes.front();//访问队首元素
            nodes.pop();//队列的第一个元素出队列
            
            int dep=depth.front();//步数初始为1
            depth.pop();
            
            for (int i=0; i<cur.size(); i++) {//改变单词的字母
                for (int j=0; j<26; j++) {//26个英文字母
                    if (cur[i]!='a'+j) {
                        string temp=cur;
                        temp[i]='a'+j;
                        if (temp==end) {
                            return dep+1;//可以转换为end,需要dep+1步
                        }
                        if (findItem(temp, dict)) {
                            nodes.push(temp);
                            depth.push(dep+1);
                        }
                    }
                }
            }
        }
        
        
        return 0;
    }
    
    bool findItem(string ts,unordered_set<string> &dict){
        //const_iterator:常数的迭代器类型的控制序列的
        //find:查找与指定键匹配的元素
        
        unordered_set<string>::const_iterator ci=dict.find(ts);
        if (ci!=dict.end()) {//找到了
            dict.erase(ci);//移除指定位置处的元素
            return true;
        }else{
            return false;//没找到
        }
        return true;
    }
};

int main(){
    string start = "hit";
    string end = "cog";
    unordered_set<string> dict = {"hot","dot","dog","lot","log"};
    Solution so;
    int res=so.ladderLength(start, end, dict);
    cout<<res<<endl;
    return 0;
}

Solution2

class Solution {
public:
    int ladderLength(string start, string end, unordered_set<string> &dict) {
        
        if (start==end) {
            return 1;
        }
        
        queue<string> nodes;
        nodes.push(start);
        
        queue<int> depth;
        depth.push(1);
        findItem(start, dict);
        
        while (!nodes.empty()) {
            
            string cur=nodes.front();
            nodes.pop();
            int dep=depth.front();
            depth.pop();
            
            for (int i=0; i<cur.size(); i++) {
                for (int j=0; j<26; j++) {
                    string temp=cur;
                    if (temp[i]!='a'+j) {
                        temp[i]='a'+j;
                        if (temp==end) {
                            return dep+1;
                        }
                        if (findItem(temp, dict)) {
                            nodes.push(temp);
                            depth.push(dep+1);
                        }
                    }
                }
            }

        }
        
        return 0;
    }
    
    bool findItem(string target,unordered_set<string> &dict){
        unordered_set<string>::const_iterator ci= dict.find(target);
        if (ci!=dict.end()) {
            dict.erase(ci);
            return true;
        }else{
            return false;
        }
    }
};


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值