• lintcode594


    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.
    Example
    Given source = abcdef, target = bcd, return 1.
     
    Rabin Karp Algorithm。用Hash方程的思想做。自己实现Hash function。
    1.提前算好target的code。
    2.开始读入source的每个字符,在for循环里计算所有长度为target.length()的子字符串的hashcode。
    3.对比,如果code一样,要进一步对比是否substring的确一样以排除false positive.
     
    细节:
    1.第二步内比如从abc -> bcd,for循环每次都加了新的字符,d已经被加上去了,你只要轻松地排除窗口刚滑走的a*幂次即可。因为幂次固定是31*target.length(),可以提早把幂次算好。
    2.对%BASE这个操作每次计算别忘了。
    3.对两个各自对BASE取余过的数做减法后,可能会出来负数,这时候不好 
     
    我的实现:
    public class Solution {
        /*
         * @param source: A source string
         * @param target: A target string
         * @return: An integer as index
         */
        public int strStr2(String source, String target) {
            // write your code here
            if (source == null || target == null) {
                return -1;
            }
            if (target.length() == 0) {
                return 0;
            }
            
            int BASE = 100000;
            int length = target.length();
            
            // 31^length, 31 is HASHBASE.
            int power = 1;
            for (int i = 0; i < length; i++) {
                power = (power * 31) % BASE;
            }
            
            int targetCode = 0;
            for (int i = 0; i < length; i++) {
                targetCode = (targetCode * 31 + target.charAt(i)) % BASE;
            }
            
            int sourceCode = 0;
            for (int i = 0; i < source.length(); i++) {
                sourceCode = (sourceCode * 31 + source.charAt(i)) % BASE;
                
                if (i >= length) {
                    //注意这里。可能出现负数的地方不要直接再%,用if处理。
                    sourceCode = sourceCode - (source.charAt(i - length) * power) % BASE;
                    if (sourceCode < 0) {
                        sourceCode += BASE;
                    }
                }
                
                if (i >= length - 1 && sourceCode == targetCode 
                    && source.substring(i - length + 1, i + 1).equals(target)) {
                    return i - length + 1;    
                }
            }
            
            return -1;
        }
    }

    九章实现:

    public class Solution {
        /**
         * @param source a source string
         * @param target a target string
         * @return an integer as index
         */
        public int strStr2(String source, String target) {
            if(target == null) {
                return -1;
            }
            int m = target.length();
            if(m == 0 && source != null) {
                return 0;
            }
            
            if(source == null) {
                return -1;
            }
            int n = source.length();
            if(n == 0) {
                return -1;
            }
    
            // mod could be any big integer
            // just make sure mod * 33 wont exceed max value of int.
            int mod = Integer.MAX_VALUE / 33;
            int hash_target = 0;
    
            // 33 could be something else like 26 or whatever you want
            for (int i = 0; i < m; ++i) {
                hash_target = (hash_target * 33 + target.charAt(i) - 'a') % mod;
                if (hash_target < 0) {
                    hash_target += mod;
                }
            }
    
            int m33 = 1;
            for (int i = 0; i < m - 1; ++i) {
                m33 = m33 * 33 % mod;
            }
    
            int value = 0;
            for (int i = 0; i < n; ++i) {
                if (i >= m) {
                    value = (value - m33 * (source.charAt(i - m) - 'a')) % mod;
                }
    
                value = (value * 33 + source.charAt(i) - 'a') % mod;
                if (value < 0) {
                    value += mod;
                }
    
                if (i >= m - 1 && value == hash_target) {
                    // you have to double check by directly compare the string
                    if (target.equals(source.substring(i - m + 1, i + 1))) {
                        return i - m + 1;
                    }
                }
            }
            return -1;
        }
    }
  • 相关阅读:
    SSM框架的基本配置
    Python开发的飞机打外星人小游戏
    python中count和index
    破解Xmind时长
    光流法简介
    Linux常用命令
    GitHub常用命令
    极大似然估计与最大后验概率估计
    在linux上加速git clone
    Endnote导入共享数据
  • 原文地址:https://www.cnblogs.com/jasminemzy/p/9429780.html
Copyright © 2020-2023  润新知