686 Repeated String Match

class Solution {
    public int repeatedStringMatch(String A, String B) {
        StringBuilder sb = new StringBuilder();
        int count = 0;
        while (sb.length() < B.length()){
            sb.append(A);
            count++;
        }

        if (sb.toString().contains(B)) return count;
        if (sb.append(A).toString().contains(B)) return ++count;

        return -1;
    }
}

392. Is Subsequence

class Solution {
    public boolean isSubsequence(String s, String t) {
        int index1 = 0, index2 = 0;

        while (index1 < s.length() && index2 < t.length()){
            char c1 = s.charAt(index1);
            char c2 = t.charAt(index2);

            if (c1 == c2){
                index1++;
                index2++;
            }
            else{
                index2++;
            }
        }

        return index1 == s.length();
    }
}

Follow up:

If there are lots of incoming S, say S1, S2, ... , Sk where k >= 1B, and you want to check one by one to see if T has its subsequence. In this scenario, how would you change your code?

/**
 * Follow-up
 * If we check each sk in this way, then it would be O(kn) time where k is the number of s and t is the length of t. 
 * This is inefficient. 
 * Since there is a lot of s, it would be reasonable to preprocess t to generate something that is easy to search for if a character of s is in t. 
 * Sounds like a HashMap, which is super suitable for search for existing stuff. 
 */
public boolean isSubsequence(String s, String t) {
    if (s == null || t == null) return false;

    Map<Character, List<Integer>> map = new HashMap<>(); //<character, index>

    //preprocess t
    for (int i = 0; i < t.length(); i++) {
        char curr = t.charAt(i);
        if (!map.containsKey(curr)) {
            map.put(curr, new ArrayList<Integer>());
        }
        map.get(curr).add(i);
    }

    int prev = -1;  //index of previous character
    for (int i = 0; i < s.length(); i++) {
        char c = s.charAt(i);

        if (map.get(c) == null)  {
            return false;
        } else {
            List<Integer> list = map.get(c);
            prev = binarySearch(prev, list, 0, list.size() - 1);
            if (prev == -1) {
                return false;
            }
            prev++;
        }
    }

    return true;
}

private int binarySearch(int index, List<Integer> list, int start, int end) {
    while (start <= end) {
        int mid = start + (end - start) / 2;
        if (list.get(mid) < index) {
            start = mid + 1;
        } else {
            end = mid - 1;
        }
    }

    return start == list.size() ? -1 : list.get(start);
}

395. Longest Substring with At Least K Repeating Characters

class Solution {
    public int longestSubstring(String s, int k) {
        if (s == null || s.length() == 0 || k == 0) return 0;
        int[] count = new int[26];

        for (char c : s.toCharArray()){
            count[c - 'a']++;
        }

        List<Integer> pos = new ArrayList<>();
        for (int i = 0; i < s.length(); i++){
            if (count[s.charAt(i) - 'a'] < k) pos.add(i);
        }

        if (pos.size() == 0) return s.length();
        int res = 0;
        pos.add(0, -1);
        pos.add(s.length());
        for (int i = 1; i < pos.size(); i++){
            int start = pos.get(i - 1) + 1;
            int end = pos.get(i);
            int next = longestSubstring(s.substring(start, end), k);
            res = Math.max(res, next);
        }

        return res;
    }
}

results matching ""

    No results matching ""