You are given a string, S, and a list of words, L, that are all of the same length. Find all starting indices of substring(s) in S that is a concatenation of each word in L exactly once and without any intervening characters.
For example, given:
S: "barfoothefoobarman"
L: ["foo", "bar"]
You should return the indices: [0,9]
.
(order does not matter).
从左往右扫描主字符串,用两个map<String, Integer>来统计字符串的出现次数. 这里L数组中可能会出现两个相同的字符串.
1 public class Solution { 2 public ArrayList<Integer> findSubstring(String S, String[] L) { 3 ArrayList<Integer> res = new ArrayList<Integer>(); 4 if(S == null || S.length() == 0 || L.length == 0){ 5 return null; 6 } 7 8 int numWords = L.length; 9 int M = S.length(); 10 int N = L[0].length(); 11 HashMap<String, Integer> expected = new HashMap<String, Integer>(); 12 HashMap<String, Integer> real = new HashMap<String, Integer>(); 13 14 for(int i = 0; i < L.length; i++){ 15 if(expected.get(L[i]) == null){ 16 expected.put(L[i],1); 17 real.put(L[i], 0); 18 }else{ 19 expected.put(L[i], expected.get(L[i])+1); 20 } 21 } 22 // i的遍历范围是S的长度,减去L中所有String的长度和 23 for(int i = 0; i <= (M-N*numWords); i++){ 24 int j = 0; 25 while(j<numWords){ 26 // 这里的j*N,j表示已经遇到的String的个数,N是L中每个String的长度 27 String tmp = S.substring(i+j*N, i+(j+1)*N); 28 if(expected.get(tmp) == null){ 29 break; 30 }else{ 31 real.put(tmp, real.get(tmp) +1); 32 // 下面的if 表示如果遇到String超过 expected了 就跳出 33 if(real.get(tmp) > expected.get(tmp)){ 34 break; 35 } 36 j++; 37 } 38 } 39 // j 表示在S中遇到L中String的个数,j == len 表示全部都遇到了 40 if(j == numWords){ 41 res.add(i); 42 } 43 // 这里是将real清零 重新计算遇到的在L中的String 44 for(int k= 0; k < L.length; k++){ 45 real.put(L[k], 0); 46 } 47 } 48 return res; 49 } 50 }