您的位置:首页 > 其它

Word Ladder II 相邻字符串接龙 BFS

2015-09-01 10:55 381 查看
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.

/*2015.9.1cyq*/
#include <iostream>
#include <vector>
#include <string>
#include <unordered_set>
#include <unordered_map>
using namespace std;

class Solution {
public:
vector<vector<string>> findLadders(string start, string end, unordered_set<string> &dict) {
vector<vector<string>> result;
unordered_set<string> cur,next;//当前层和下一层
unordered_set<string> visited;
unordered_map<string,vector<string>> preNode;
bool found=false;

cur.insert(start);
while(!cur.empty()&&!found){
for(auto it=cur.begin();it!=cur.end();it++)
visited.insert(*it);//本层结点全设置为访问过
for(auto it=cur.begin();it!=cur.end();it++){
vector<string> newWords=nextWords(*it,end,dict,visited);
for(auto ik=newWords.begin();ik!=newWords.end();++ik){
if(*ik==end) found=true;
next.insert(*ik);//通过多种路径到达新结点时会自动去重
preNode[*ik].push_back(*it);//记录前驱结点
}
}
cur.clear();
swap(cur,next);
}
if(found){
vector<string> path;
dfs(preNode,start,end,path,result);
}
return result;
}
private:
//利用前驱map,从end向start,dfs出所有路径
void dfs(unordered_map<string,vector<string>> &preNode,string &start,string &word,
vector<string> &path,vector<vector<string>> &result){
path.push_back(word);
if(word==start){
result.push_back(path);
reverse(result.back().begin(),result.back().end());
}else{
for(auto it=preNode[word].begin();it!=preNode[word].end();++it)
dfs(preNode,start,*it,path,result);
}
path.pop_back();
}
//获取与s相差一个字符的字符串,要求该字符串未被访问过
//注意找到新字符串后,先不标记为访问过,因为可能通过多种路径找到新字符串,所有路径都要输出
vector<string> nextWords(const string &s,const string &target,unordered_set<string> &dict,
unordered_set<string> &visited){

vector<string> result;
for(int i=0;i<s.size();i++){
string tmp(s);
for(char c='a';c<='z';c++){
if(tmp[i]==c) continue;
swap(c,tmp[i]);
if((dict.find(tmp)!=dict.end()||tmp==target)&&visited.find(tmp)==visited.end())
result.push_back(tmp);
swap(c,tmp[i]);
}
}
return result;
}
};

int main(){
string start="hit";
string end="cog";
string a[]={"hot","dot","dog","lot","log"};
int n=sizeof(a)/sizeof(string);
unordered_set<string> dict;
for(int i=0;i<n;i++)
dict.insert(a[i]);

Solution solu;
vector<vector<string>> ret=solu.findLadders(start,end,dict);
for(auto it=ret.begin();it!=ret.end();++it){
for(auto ik=(*it).begin();ik!=(*it).end();++ik)
cout<<*ik<<" ";
cout<<endl;
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: