zoukankan      html  css  js  c++  java
  • 30. 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.

    Example 1:

    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.
    

    Example 2:

    Input:
      s = "wordgoodstudentgoodword",
      words = ["word","student"]
    Output: []

    解题思路:

    这道题可以用哈希表来记录每个单词的个数(因为有的test case里有重复的词语出现)

    对map中的每一对键值对中的key,也就是单词,都有串联以他为开始的可能,所以我们针对这些可能性进行遍历。

    我写了一个辅助函数进行判断以该位置开头的子串能否构成符合题目要求的子字符串:

      因为给出的单词的长度都相同,所以我们可以直接取长度,然后判断该单词是否在map中:

        1.若不在map中则无效,若在map中出现个数为0,也无效。

        2.若在map中,出现个数大于0,则可以进行下一个单词的判断,不要忘记对map中的值进行修改辅助判断!

    这里需要注意的是:

      1.在对开头可能进行判断的循环中,start的递增幅度为start++,而不是start += wLen。

       后者无法通过{"aa", "aa", "aa"} s = "aaaaaaaa"这个例子

          2. 在辅助函数中,不要忘记对start进行递增操作,这里可以为 start += wLen

    代码:

    class Solution {
    public:
        vector<int> findSubstring(string s, vector<string>& words) {
            vector<int> ret;
            if(words.empty())
                return ret;
            int num = words.size();
            int wLen = words[0].size();
            if(s.empty() || wLen > s.size() || (num * wLen > s.size()))
                return ret;
            
            unordered_map<string, int> wordTimes; //prevent repeat
            for(int i = 0; i < words.size(); i++){
                wordTimes[words[i]]++;
            }
            
            for(auto wpair: wordTimes){
            int start = 0;
            while(start > -1){
                start = (int)s.find(wpair.first, start);
                if(start != -1){if(isValid(wordTimes, s, start, wLen, num))
                        ret.push_back(start);
                    start ++;
                }
            }
        }
            return ret;
            
        }
    private:
        bool isValid(unordered_map<string, int> wordTimes, string str, int start, int wLen, int nums){
            for(int i = 0; i < nums; i++){
                if(start >= str.size())
                    return false;
                string tmp = str.substr(start, wLen);
                if(wordTimes.count(tmp) == 0 || wordTimes[tmp] == 0){
                    return false;
                }
                wordTimes[tmp]--;
                start += wLen;
            }
            return true;
        }
    };
  • 相关阅读:
    将CSV格式的文件导入到数据中
    查询及删除数据重复记录的方法
    创建job
    存储过程动态创建表,以时间给表命名
    索引表空间
    sequence 作为序列插入值不是第一个
    2.类(对象)之间的关系
    1.类和对象
    angularJS1笔记-(1)-多控制器
    angularJS中$apply()方法详解
  • 原文地址:https://www.cnblogs.com/yaoyudadudu/p/9153679.html
Copyright © 2011-2022 走看看