Substring with Concatenation of All Words

  • 问题介绍
    • 问题描述:
      • You are given a string, s, and a list of words, words, that are all of the same length. Find all starting indices of substring(s) in s that is a concatenation of each word in words exactly once and without any intervening characters.
    • 示例:
      • Input:S = “barfoothefoobarman”,words = [“foo”,“bar”];
      • Output:[0,9]
      • Explanation:Substrings starting at index 0 and 9 are “barfoor” and “foobar” respectively.The output order does not matter, returning [9,0] is fine too.
    • 约束条件:NULL
  • 解决思路
    • 思路:
      • 分析题目后,可以想到题目可以分解为两部分:1.字符串的子串匹配;2.子串的拼接;可以想到的暴力解决方法为,将words中所有的单词存在的组合拼接出来,然后作为子串,挨个与带匹配字符串S进行匹配,虽然可行,但是时间复杂度过高;
      • 对于子串的拼接,可以维护一个包含所有words的vector dic,每当成功匹配一个dic中的字符串就将dic中对应的那个字符串删除,若是匹配dic中包含的所有子串都匹配失败,则表示字符串S的当前位置不是我们所要求的,则将dic恢复为初始化words;
      • 对于每一个dic中的子串,将当前S字符串遍历到的位置i保存下来,进行匹配,当dic中的子串全部遍历后,如果dic没有为空,则表示S字符串当前的位置不满足要求,进行i++的操作,否表示i为我们需要求的S字符串的位置,将i存入vector resp结果中;对于S字符串的遍历不需要遍历全部长度,因为最后需要预留一个words中所有子串的长度和,所以遍历的实际长度为:s.length()-(lxwords.size())+1即可;
    • 问题: 该算法的时间复杂度为O(s.length()xwords.size()xwords[0].length()),在LeetCode提交结果显示并不太好,属于刚刚能通过时间复杂度检验的水平,还有待改进;
  • 代码
class Solution {
public:
    vector<int> findSubstring(string s, vector<string>& words) {
        vector<int> resp;
        vector<int> pos;
        vector<string> dic;
        int sign=-1;
        int l;
        if(words.empty())
        {
            return resp;
        }
        else
        {
            l=words[0].length();
            dic.assign(words.begin(),words.end());
        }
        
        if(s.empty())
        {
            return resp;
        }
        else 
        {   
            int count=s.length()-(l*words.size())+1;
            for(int i=0;i<count;i++)
            {
                int x=i;
                int j=0;
                while(j<dic.size())
                {
                    int z=0;
                    while(z<dic[j].length()&&s[x+z]==dic[j][z])
                    {
                        z++;
                    }
                    if(z==dic[j].length())
                    {
                        dic.erase(dic.begin()+j);
                        x+=l;
                        j=0;
                    }
                    else
                    {
                        j++;             
                    }
                }
                if(dic.empty())
                {
                    resp.push_back(i);
                }
                dic.clear();
                dic.assign(words.begin(),words.end());
            }
            return resp;
        }
    }
};
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值