Description
Implement strStr
function in O(n + m) time.
strStr
return the first index of the target string in a source string. The length of the target string is m and the length of the source string is n.
If target does not exist in source, just return -1.
Have you met this question in a real interview? Yes
Problem Correction
Example
Example 1:
Input:source = "abcdef", target = "bcd"
Output:1
Explanation:
The position of the first occurrence of a string is 1.
Example 2:
Input:source = "abcde", target = "e"
Output:4
Explanation:
The position of the first occurrence of a string is 4.
思路:用for循环可以写出:n*m的代码,但是题目要求n+m, 思路就是用hash function把字符串的比较变换成hash 数字的比较,这样可以把字符串O(m)的时间缩短为O(1); Time Complexity: O(n+m);
public class Solution {
int BASE = 100000;
/*
* @param source: A source string
* @param target: A target string
* @return: An integer as index
*/
public int strStr2(String source, String target) {
if(source == null || target == null || target.length() > source.length()) {
return -1;
}
if(target.length() == 0 ){
return 0;
}
int n = source.length();
int m = target.length();
int power = 1;
// BASE ^ m;
for(int i = 0; i < m; i++) {
power = (power * 31) % BASE;
}
// calculate target hash code;
int targetHash = 0;
for(int i = 0; i < m; i++) {
targetHash = (targetHash * 31 + target.charAt(i)) % BASE;
}
int sourceHash = 0;
for(int i = 0; i < n ; i++) {
// abc + d;
sourceHash = (sourceHash * 31 + source.charAt(i)) % BASE;
if(i < m - 1) {
continue;
}
// bcd - a;
if(i >= m) {
sourceHash = sourceHash - (source.charAt(i-m) * power ) % BASE;
if(sourceHash < 0) {
sourceHash += BASE;
}
}
// i == m -1;
if(sourceHash == targetHash) {
// check real string;
if(source.substring(i-m+1, i+1).equals(target)){
return i - m + 1;
}
}
}
return -1;
}
}
O(n*m)的算法:
class Solution {
public int strStr(String haystack, String needle) {
if(haystack == null || needle == null) {
return 0;
}
for(int i = 0; i <= haystack.length() - needle.length(); i++) {
int j = 0;
int k = i;
while(j < needle.length()) {
if(haystack.charAt(k) == needle.charAt(j)) {
k++;
j++;
} else {
break;
}
}
if(j == needle.length()) {
return i;
}
}
return -1;
}
}