[LeetCode] 686. Repeated String Match 重复字符串匹配
Given two strings A and B, find the minimum number of times A has to be repeated such that B is a substring of it. If no such solution, return -1.
For example, with A = "abcd" and B = "cdabcdab".
Return 3, because by repeating A three times (“abcdabcdabcd”), B is a substring of it; and B is not a substring of A repeated two times ("abcdabcd").
Note:
The length of A
and B
will be between 1 and 10000.
给2个字符串,找到字符串A需要重复的次数,使得字符串B是字符串A的子串,如果没有答案,则返回-1。
解法1: Brute fore. a modified version of string find, which does not stop at the end of A, but continue matching by looping through A
解法2: KMP, O(n + m) version that uses a prefix table (KMP)
解法3: Rabin-Karp Algorithm
Java: 1
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | class Solution { public int repeatedStringMatch(String A, String B) { StringBuilder sb = new StringBuilder(); sb.append(A); int count = 1 ; while (sb.indexOf(B)< 0 ){ if (sb.length()-A.length()>B.length()){ return - 1 ; } sb.append(A); count++; } return count; } |
Python: 1
1 2 3 4 5 6 7 8 9 10 11 12 13 | class Solution( object ): def repeatedStringMatch( self , A, B): """ :type A: str :type B: str :rtype: int """ sa, sb = len (A), len (B) x = 1 while (x - 1 ) * sa < = 2 * max (sa, sb): if B in A * x: return x x + = 1 return - 1 |
Python: 3
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 | # Time: O(n + m) # Space: O(1) class Solution( object ): def repeatedStringMatch( self , A, B): """ :type A: str :type B: str :rtype: int """ def check(index): return all (A[(i + index) % len (A)] = = c for i, c in enumerate (B)) M, p = 10 * * 9 + 7 , 113 p_inv = pow (p, M - 2 , M) q = ( len (B) + len (A) - 1 ) / / len (A) b_hash, power = 0 , 1 for c in B: b_hash + = power * ord (c) b_hash % = M power = (power * p) % M a_hash, power = 0 , 1 for i in xrange ( len (B)): a_hash + = power * ord (A[i % len (A)]) a_hash % = M power = (power * p) % M if a_hash = = b_hash and check( 0 ): return q power = (power * p_inv) % M for i in xrange ( len (B), (q + 1 ) * len (A)): a_hash = (a_hash - ord (A[(i - len (B)) % len (A)])) * p_inv a_hash + = power * ord (A[i % len (A)]) a_hash % = M if a_hash = = b_hash and check(i - len (B) + 1 ): return q if i < q * len (A) else q + 1 return - 1 |
C++: 1
1 2 3 4 5 6 7 | int repeatedStringMatch(string A, string B) { for ( auto i = 0, j = 0; i < A.size(); ++i) { for (j = 0; j < B.size() && A[(i + j) % A.size()] == B[j]; ++j); if (j == B.size()) return (i + j) / A.size() + ((i + j) % A.size() != 0 ? 1 : 0); } return -1; } |
C++: 2
1 2 3 4 5 6 7 8 9 10 11 12 13 | int repeatedStringMatch(string a, string b) { vector< int > prefTable(b.size() + 1); // 1-based to avoid extra checks. for ( auto sp = 1, pp = 0; sp < b.size(); ) { if (b[pp] == b[sp]) prefTable[++sp] = ++pp; else if (pp == 0) prefTable[++sp] = pp; else pp = prefTable[pp]; } for ( auto i = 0, j = 0; i < a.size(); i += max(1, j - prefTable[j]), j = prefTable[j]) { while (j < b.size() && a[(i + j) % a.size()] == b[j]) ++j; if (j == b.size()) return (i + j) / a.size() + ((i + j) % a.size() != 0 ? 1 : 0); } return -1; } |
C++:
1 2 3 4 5 6 7 8 9 10 11 | class Solution { public : int repeatedStringMatch(string A, string B) { string t = A; for ( int i = 1; i <= B.size() / A.size() + 2; ++i) { if (t.find(B) != string::npos) return i; t += A; } return -1; } }; |
C++:
1 2 3 4 5 6 7 8 9 10 11 12 | class Solution { public : int repeatedStringMatch(string A, string B) { int m = A.size(), n = B.size(); for ( int i = 0; i < m; ++i) { int j = 0; while (j < n && A[(i + j) % m] == B[j]) ++j; if (j == n) return (i + j - 1) / m + 1; } return -1; } }; |
类似题目:
[LeetCode] 459. Repeated Substring Pattern 重复子字符串模式
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步