leetcode -- string

Topic overview

Link with leetcode

    1. Reverse string
    1. Reverse string II
  1. Sword finger Offer 05 Replace spaces
    1. Flip the words in the string
  2. Sword finger Offer58-II Left rotation string
  3. 28.Implement str ()
    1. Duplicate substring

Sub topic explanation

344 reverse string
If the key part of the problem can be solved directly with library functions, it is recommended not to use library functions

If the library function is only a small part of the problem-solving process, and you already know the internal implementation principle of the library function, you can consider using the library function.

    public void reverseString(char[] s) {
        int head = 0;
        int end = s.length - 1;
        char tmp;
        while (head < end){
            tmp = s[end];
            s[end] = s[head];
            s[head] = tmp;
            head++;
            end--;
        }
    }

541 reverse string ii

class Solution {
    public String reverseStr(String s, int k) {
        char[] arr = s.toCharArray();
        int len = s.length();
        int head = 0;
        int last = 2 * k - 1;
        while (last <= len - 1){
            reverse(head, head + k - 1, arr);
            last += 2 * k;
            head += 2 * k;
        }
        int end = (len - 1 - head < k) ? len - 1 : head + k - 1;
        reverse(head, end, arr);
        return String.valueOf(arr);
    }

    public void reverse(int first, int end, char[] arr){
        while (first < end){
            char tmp = arr[first];
            arr[first] = arr[end];
            arr[end] = tmp;
            first++;
            end--;
        }
    }
}

Plan and then decide
Block first

  • Enough 2k
    Exchange function
  • Not enough 2k
    Less than k-exchange function
    Greater than k, less than 2k - exchange function

Replace spaces with sword finger Offer5

class Solution {
    public String replaceSpace(String s) {
    	//Single thread faster with StringBuffer
        StringBuffer stb = new StringBuffer();
        for (int i = 0; i < s.length(); i++) {
            char point = s.charAt(i); 
            if (point == ' '){
                stb.append("%20");
            }else {
                stb.append(point);
            }
        }
        return stb.toString();
    }
}

Here is another idea:
1. The original string space can be expanded to accommodate newly changed characters.
2. Locate the last character of the original string
3. Locate the last character of the new string
4. Comparison and replication

public String replaceSpace(String s) {
    if(s == null || s.length() == 0){
        return s;
    }
    //Expand the space and double the number of spaces
    StringBuilder str = new StringBuilder();
    for (int i = 0; i < s.length(); i++) {
        if(s.charAt(i) == ' '){
            str.append("  ");
        }
    }
    //If there is no space, return directly
    if(str.length() == 0){
        return s;
    }
    //Define two pointers with spaces
    int left = s.length() - 1;//Left pointer: points to the last position of the original string
    s += str.toString();
    int right = s.length()-1;//Right pointer: points to the last position of the extended string
    char[] chars = s.toCharArray();
    while(left>=0){
        if(chars[left] == ' '){
            chars[right--] = '0';
            chars[right--] = '2';
            chars[right] = '%';
        }else{
            chars[right] = chars[left];
        }
        left--;
        right--;
    }
    return new String(chars);
}

151. Flip the words in the string
Method 1: compare the water, use the split function in the string, additional O(N) space, and finally string them together. Note that remove the last space and when there are continuous separators, such as two spaces. After the segmentation, it is "" and judged with. equals()
Method 2: reverse all characters, and finally reverse the words. The final time complexity is O(1). Execute step by step, and remove redundant spaces at the beginning. Inverts all strings. Reverse the words.

	//FA Yi
    public static String reverseWords(String s) {
        String[] s1 = s.split(" ");
        StringBuffer stb = new StringBuffer();
        for (int i = s1.length - 1; i >= 0; i--){
            if (!s1[i].equals("")) {
                stb.append(s1[i] + " ");
            }
        }
        //Remove last space
        return stb.toString().substring(0,stb.length() - 1);
    }

    public static void main(String[] args) {
        System.out.println(reverseWords("We      are happy"));//happy are We
    }
//Method II
class Solution {
   /**
     * Not implemented using Java built-in methods
     * <p>
     * 1.Remove excess spaces at the beginning and end and in the middle
     * 2.Inverts the entire string
     * 3.Reverse each word
     */
    public String reverseWords(String s) {
        // System.out.println("ReverseWords.reverseWords2() called with: s = [" + s + "]");
        // 1. Remove the beginning, end and middle excess spaces
        StringBuilder sb = removeSpace(s);
        // 2. Invert the entire string
        reverseString(sb, 0, sb.length() - 1);
        // 3. Reverse each word
        reverseEachWord(sb);
        return sb.toString();
    }

    private StringBuilder removeSpace(String s) {
        // System.out.println("ReverseWords.removeSpace() called with: s = [" + s + "]");
        int start = 0;
        int end = s.length() - 1;
        while (s.charAt(start) == ' ') start++;
        while (s.charAt(end) == ' ') end--;
        StringBuilder sb = new StringBuilder();
        while (start <= end) {
            char c = s.charAt(start);
            if (c != ' ' || sb.charAt(sb.length() - 1) != ' ') {
                sb.append(c);
            }
            start++;
        }
        // System.out.println("ReverseWords.removeSpace returned: sb = [" + sb + "]");
        return sb;
    }

    /**
     * Inverts the characters of the specified interval [start, end] of the string
     */
    public void reverseString(StringBuilder sb, int start, int end) {
        // System.out.println("ReverseWords.reverseString() called with: sb = [" + sb + "], start = [" + start + "], end = [" + end + "]");
        while (start < end) {
            char temp = sb.charAt(start);
            sb.setCharAt(start, sb.charAt(end));
            sb.setCharAt(end, temp);
            start++;
            end--;
        }
        // System.out.println("ReverseWords.reverseString returned: sb = [" + sb + "]");
    }

    private void reverseEachWord(StringBuilder sb) {
        int start = 0;
        int end = 1;
        int n = sb.length();
        while (start < n) {
            while (end < n && sb.charAt(end) != ' ') {
                end++;
            }
            reverseString(sb, start, end - 1);
            start = end + 1;
            end = start + 1;
        }
    }
}

Sword finger Offer58-II. Left rotation string
Method 1: comparing water is to use substring
In fact, the time complexity of using substr and inversion is the same, both of which are O(n), but using substr applies for additional space, so the space complexity is O(n), and the space complexity of inversion method is O(1).
Method 2: you can directly use inversion without substring. An interesting idea is:

//Method I:
    public String reverseLeftWords(String s, int n) {
        StringBuilder sb = new StringBuilder();
        sb.append(s.substring(n)+s.substring(0,n));
        return sb.toString();
    }
//Method 2:
class Solution {
    public String reverseLeftWords(String s, int n) {
        int len=s.length();
        StringBuilder sb=new StringBuilder(s);
        reverseString(sb,0,n-1);
        reverseString(sb,n,len-1);
        return sb.reverse().toString();
    }
     public void reverseString(StringBuilder sb, int start, int end) {
        while (start < end) {
            char temp = sb.charAt(start);
            sb.setCharAt(start, sb.charAt(end));
            sb.setCharAt(end, temp);
            start++;
            end--;
            }
        }
}

28. Implement str ()
The violent solution must not work. Here is a good api, the KMP algorithm. It is very important. It is recommended to memorize it
KMP algorithm

    public static int strStr(String haystack, String needle) {
        if (needle.equals("")) return 0;//Each topic has different requirements and waits for the opportunity
        if (haystack.length() == 0 || needle.length() == 0 || haystack.length() < needle.length()) return -1;
        char[] str1 = haystack.toCharArray();
        char[] str2 = needle.toCharArray();
        //Create the next[i] array and store the length of the longest (prefix and suffix equal) before the ith character of str2. Note that the string itself is not included
        int[] next = new int[str2.length];
        next[0] = -1;
        if (str2.length > 1){//Prevent str2 from having only one character
            next[1] = 0;
        }
        int i = 2;
        //The initial cn records the value of next[i- 1]. Since the initial value of i here is 2, next[i-1] = 0, so cn = 0;
        int cn = 0;
        while (i < str2.length){
            if (str2[i - 1] == str2[cn]){
                next[i++] = ++cn;
            }else if (cn == 0){
                next[i++] = 0;
            }else {
                cn = next[cn];
            }
        }
        //Using next [] array to solve string matching problem
        int t1 = 0; int t2 = 0;
        while (t1 < str1.length && t2 < str2.length){
            if (str1[t1] == str2[t2]){
                t1++;
                t2++;
            }else if (t2 == 0){
                t1++;
            }else {
                t2 = next[t2];
            }
        }
        return t2 == str2.length ? t1 - t2 : -1;
    }

    public static void main(String[] args) {
        String haystack = "abcdeabcfee";
        String needle = "d";
        System.out.println(strStr(haystack,needle));
    }

29. Duplicate substrings
I really didn't know to use KMP algorithm at first, but because it depends on whether it is a repeated string, the array of next [] is absolutely regular. You can run several next [] arrays to see the following rules:

public static boolean repeatedSubstringPattern(String s) {
        if (s.length() < 2) return false;
        //KMP algorithm can be used to think that there must be corresponding rules in the next [] array
        char[] arr = s.toCharArray();
        int n = s.length();
        int[] next = new int[n + 1];
        next[0] = -1;
        next[1] = 0;
        int i = 2;
        int cn = 0;
        while (i <= n){
            if (arr[i - 1] == arr[cn]){
                next[i++] = ++cn;
            }else if (cn == 0){
                next[i++] = 0;
            }else {
                cn = next[cn];
            }
        }
        for (int h : next){
            System.out.println(h);
        }
        if (next[n] != 0 && n % (n - (next[n])) == 0){
            return true;
        }
        return false;
    }

    public static void main(String[] args) {
        String haystack = "abcabcabc";
        System.out.println(repeatedSubstringPattern(haystack));
    }

summary

  1. It is suggested that if the key part of the problem can be solved directly with library functions, it is recommended not to use library functions. If the library function is only a small part of the problem-solving process, and you already know the internal implementation principle of the library function, you can consider using the library function.
  2. Double pointer method is commonly used in arrays, linked lists and strings. For many array filling problems, you can first expand the array with the filled size in advance, and then operate from the back to the front
  3. When you need a fixed rule to process strings paragraph by paragraph, you should think about making an article on the expression of the for loop. There is an idea: first overall inversion and then local inversion, first local inversion and then overall inversion
  4. The main idea of KMP is that when there is a string mismatch, you can know part of the previously matched text content, and you can use this information to avoid matching from the beginning---- The most important algorithm in string

Tags: Java Algorithm leetcode string

Posted on Tue, 23 Nov 2021 10:13:42 -0500 by Ollie Saunders