[LeetCode] Word Ladder

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

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

Note:

  • Return 0 if there is no such transformation sequence.
  • All words have the same length.
  • All words contain only lowercase alphabetic characters.

以下两种方法的思路几乎一样,但方法1:Time Limit Exceeded!方法2:Accept。

原因是:方法1找邻近字符串,是遍历dict中的每个字符串,对比两两字符串之间的每个字母,如果只有一个字母不同则视为neighbor,即代码中的isNeighbor()函数;方法2,是将一个字符串中的每个字母依次在‘a’-‘z’之间改变,即先得到neighbor字符串,然后查找这个字符串是不是在dict中。由于dict可能会非常大,而dict中的每个字符串的长度会比较小,所以用方法2的时间复杂度比较小。(即:Using isNeighbor seems to be slower than changing every position from 'a' to 'z'.)

方法1:

    bool isNeighbor(string a,string b)
    {
        int diffNum = 0;
        bool res = true;
        for(int i=0;i<a.size();i++){
            if(a[i]!=b[i] && ++diffNum != 1){
               res = false;
               break;
            }     
        }//end for
        return res;    
    }
class Solution {
public:
    int ladderLength(string start, string end, unordered_set<string> &dict) {
        if(dict.size()<1)
            return 0;

        int num = 0;
        int len = start.size();
        pair<string,int> pa(start,1);//key表示在寻找路径中出现的字符串,value表示此字符串是字符串组的第几个
        queue<pair<string,int>> q;
        q.push(pa);
        num = bfs(dict,q,end);
        return num;
    }
private:

    int bfs(unordered_set<string> &dict,queue<pair<string,int>> &q,string &end)
    {
        int  curNum = 1;
        while(!q.empty()){
            pair<string,int> pa = q.front();
            q.pop();
            string curS = pa.first;
            curNum = pa.second;
            if(curS == end)
            {
               break;
            }                
            vector<string> BeDeleted;
            for(unordered_set<string>::iterator iter = dict.begin();iter != dict.end();iter++){
                if(isNeighbor(*iter,curS)){
                    BeDeleted.push_back(*iter);
                    pa = make_pair(*iter,curNum+1);
                    q.push(pa);
                }  
            }//end for
            for(int i=0;i<BeDeleted.size();i++)
            {
               dict.erase(BeDeleted[i]);
            }
        }//end while
        return curNum;
    }
};

方法2:Accept

string NeighborIsInDict(queue<pair<string,int>> &q,unordered_set<string> &dict,string &curS,int &curNum,string &end)
    {
       string s(curS);
       int len = curS.size();
       for(int i = 0;i<len;i++)
       {
          s = curS;
          for(int j=0;j<26;j++)
          {
             s[i]='a'+j;
             if(s==curS)
                 continue;
             else if(s==end)
                 {
                     curNum++;
                     return end;
                 }
             else if(s!=curS && dict.count(s))
             {
                 dict.erase(s);
                 q.push(make_pair(s,curNum+1));
             }          
          }//end for       
       }//end for
       return s;
    }
class Solution {
public:
    int ladderLength(string start, string end, unordered_set<string> &dict) {
        if(dict.size()<1)
            return 0;

        int num = 0;
        int len = start.size();
        pair<string,int> pa(start,1);//key表示在寻找路径中出现的字符串,value表示此字符串是字符串组的第几个
        queue<pair<string,int>> q;
        q.push(pa);
        num = bfs(dict,q,end);
        return num;
    }
private:

    int bfs(unordered_set<string> &dict,queue<pair<string,int>> &q,string &end)
    {
        int  curNum = 0;
        while(!q.empty()){
            pair<string,int> pa = q.front();
            q.pop();
            string curS = pa.first;
            curNum = pa.second;
            if(curS == end)
            {
               break;
            }                    
            string s0 = NeighborIsInDict(q,dict,curS,curNum,end);
            if(s0 == end)
                return curNum;
        }//end while
        return 0;
    }
};

 

posted @ 2014-07-31 17:43  Xylophone  Views(186)  Comments(0Edit  收藏  举报