leetcode 686. Repeated String Match | 686. 重复叠加字符串匹配(KMP)

x33g5p2x  于2021-11-12 转载在 其他  
字(1.1k)|赞(0)|评价(0)|浏览(503)

题目

https://leetcode.com/problems/repeated-string-match/

题解

套了 KMP 模板,O(n) 复杂度。分析如下。

  1. class Solution {
  2. public int repeatedStringMatch(String a, String b) {
  3. int repeatedTimes = Math.max((int) Math.ceil((float) 2 * b.length() / a.length()), 2);
  4. int index = indexOf(a.repeat(repeatedTimes), b);
  5. if (index == -1) return -1;
  6. return (int) Math.ceil((float) (index + b.length()) / a.length());
  7. }
  8. // KMP, find index of s2 from s1
  9. public static int indexOf(String s1, String s2) {
  10. if (s1 == null || s2 == null || s2.length() < 1 || s1.length() < s2.length()) {
  11. return -1;
  12. }
  13. char[] str1 = s1.toCharArray();
  14. char[] str2 = s2.toCharArray();
  15. int x = 0;
  16. int y = 0;
  17. // O(M) m <= n
  18. int[] next = nextArray(str2);
  19. // O(N)
  20. while (x < str1.length && y < str2.length) {
  21. if (str1[x] == str2[y]) {
  22. x++;
  23. y++;
  24. } else if (next[y] == -1) { // y == 0
  25. x++;
  26. } else {
  27. y = next[y];
  28. }
  29. }
  30. return y == str2.length ? x - y : -1;
  31. }
  32. public static int[] nextArray(char[] str2) {
  33. if (str2.length == 1) {
  34. return new int[]{-1};
  35. }
  36. int[] next = new int[str2.length];
  37. next[0] = -1;
  38. next[1] = 0;
  39. int i = 2; // 目前在哪个位置上求next数组的值
  40. int cn = 0; // 当前是哪个位置的值再和i-1位置的字符比较
  41. while (i < next.length) {
  42. if (str2[i - 1] == str2[cn]) { // 配成功的时候
  43. next[i++] = ++cn;
  44. } else if (cn > 0) {
  45. cn = next[cn];
  46. } else {
  47. next[i++] = 0;
  48. }
  49. }
  50. return next;
  51. }
  52. }

相关文章