Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit 2618f2d

Browse files
feat: add solutions to lc problem: No.3292 (doocs#3866)
No.3292.Minimum Number of Valid Strings to Form Target II
1 parent 8070bfc commit 2618f2d

File tree

6 files changed

+795
-8
lines changed

6 files changed

+795
-8
lines changed

‎solution/3200-3299/3292.Minimum Number of Valid Strings to Form Target II/README.md‎

Lines changed: 265 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -102,25 +102,286 @@ tags:
102102
#### Python3
103103

104104
```python
105-
105+
class Hashing:
106+
__slots__ = ["mod", "h", "p"]
107+
108+
def __init__(self, s: List[str], base: int, mod: int):
109+
self.mod = mod
110+
self.h = [0] * (len(s) + 1)
111+
self.p = [1] * (len(s) + 1)
112+
for i in range(1, len(s) + 1):
113+
self.h[i] = (self.h[i - 1] * base + ord(s[i - 1])) % mod
114+
self.p[i] = (self.p[i - 1] * base) % mod
115+
116+
def query(self, l: int, r: int) -> int:
117+
return (self.h[r] - self.h[l - 1] * self.p[r - l + 1]) % self.mod
118+
119+
120+
class Solution:
121+
def minValidStrings(self, words: List[str], target: str) -> int:
122+
def f(i: int) -> int:
123+
l, r = 0, min(n - i, m)
124+
while l < r:
125+
mid = (l + r + 1) >> 1
126+
sub = hashing.query(i + 1, i + mid)
127+
if sub in s[mid]:
128+
l = mid
129+
else:
130+
r = mid - 1
131+
return l
132+
133+
base, mod = 13331, 998244353
134+
hashing = Hashing(target, base, mod)
135+
m = max(len(w) for w in words)
136+
s = [set() for _ in range(m + 1)]
137+
for w in words:
138+
h = 0
139+
for j, c in enumerate(w, 1):
140+
h = (h * base + ord(c)) % mod
141+
s[j].add(h)
142+
ans = last = mx = 0
143+
n = len(target)
144+
for i in range(n):
145+
dist = f(i)
146+
mx = max(mx, i + dist)
147+
if i == last:
148+
if i == mx:
149+
return -1
150+
last = mx
151+
ans += 1
152+
return ans
106153
```
107154

108155
#### Java
109156

110157
```java
111-
158+
class Hashing {
159+
private final long[] p;
160+
private final long[] h;
161+
private final long mod;
162+
163+
public Hashing(String word, long base, int mod) {
164+
int n = word.length();
165+
p = new long[n + 1];
166+
h = new long[n + 1];
167+
p[0] = 1;
168+
this.mod = mod;
169+
for (int i = 1; i <= n; i++) {
170+
p[i] = p[i - 1] * base % mod;
171+
h[i] = (h[i - 1] * base + word.charAt(i - 1)) % mod;
172+
}
173+
}
174+
175+
public long query(int l, int r) {
176+
return (h[r] - h[l - 1] * p[r - l + 1] % mod + mod) % mod;
177+
}
178+
}
179+
180+
class Solution {
181+
private Hashing hashing;
182+
private Set<Long>[] s;
183+
184+
public int minValidStrings(String[] words, String target) {
185+
int base = 13331, mod = 998244353;
186+
hashing = new Hashing(target, base, mod);
187+
int m = Arrays.stream(words).mapToInt(String::length).max().orElse(0);
188+
s = new Set[m + 1];
189+
Arrays.setAll(s, k -> new HashSet<>());
190+
for (String w : words) {
191+
long h = 0;
192+
for (int j = 0; j < w.length(); j++) {
193+
h = (h * base + w.charAt(j)) % mod;
194+
s[j + 1].add(h);
195+
}
196+
}
197+
198+
int ans = 0;
199+
int last = 0;
200+
int mx = 0;
201+
int n = target.length();
202+
for (int i = 0; i < n; i++) {
203+
int dist = f(i, n, m);
204+
mx = Math.max(mx, i + dist);
205+
if (i == last) {
206+
if (i == mx) {
207+
return -1;
208+
}
209+
last = mx;
210+
ans++;
211+
}
212+
}
213+
return ans;
214+
}
215+
216+
private int f(int i, int n, int m) {
217+
int l = 0, r = Math.min(n - i, m);
218+
while (l < r) {
219+
int mid = (l + r + 1) >> 1;
220+
long sub = hashing.query(i + 1, i + mid);
221+
if (s[mid].contains(sub)) {
222+
l = mid;
223+
} else {
224+
r = mid - 1;
225+
}
226+
}
227+
return l;
228+
}
229+
}
112230
```
113231

114232
#### C++
115233

116234
```cpp
117-
235+
class Hashing {
236+
private:
237+
vector<long long> p;
238+
vector<long long> h;
239+
long long mod;
240+
241+
public:
242+
Hashing(const string& word, long long base, int mod) {
243+
int n = word.size();
244+
p.resize(n + 1);
245+
h.resize(n + 1);
246+
p[0] = 1;
247+
this->mod = mod;
248+
for (int i = 1; i <= n; i++) {
249+
p[i] = (p[i - 1] * base) % mod;
250+
h[i] = (h[i - 1] * base + word[i - 1]) % mod;
251+
}
252+
}
253+
254+
long long query(int l, int r) {
255+
return (h[r] - h[l - 1] * p[r - l + 1] % mod + mod) % mod;
256+
}
257+
};
258+
259+
class Solution {
260+
public:
261+
int minValidStrings(vector<string>& words, string target) {
262+
int base = 13331, mod = 998244353;
263+
Hashing hashing(target, base, mod);
264+
int m = 0, n = target.size();
265+
for (const string& word : words) {
266+
m = max(m, (int) word.size());
267+
}
268+
269+
vector<unordered_set<long long>> s(m + 1);
270+
for (const string& w : words) {
271+
long long h = 0;
272+
for (int j = 0; j < w.size(); j++) {
273+
h = (h * base + w[j]) % mod;
274+
s[j + 1].insert(h);
275+
}
276+
}
277+
278+
auto f = [&](int i) -> int {
279+
int l = 0, r = min(n - i, m);
280+
while (l < r) {
281+
int mid = (l + r + 1) >> 1;
282+
long long sub = hashing.query(i + 1, i + mid);
283+
if (s[mid].count(sub)) {
284+
l = mid;
285+
} else {
286+
r = mid - 1;
287+
}
288+
}
289+
return l;
290+
};
291+
292+
int ans = 0, last = 0, mx = 0;
293+
for (int i = 0; i < n; i++) {
294+
int dist = f(i);
295+
mx = max(mx, i + dist);
296+
if (i == last) {
297+
if (i == mx) {
298+
return -1;
299+
}
300+
last = mx;
301+
ans++;
302+
}
303+
}
304+
return ans;
305+
}
306+
};
118307
```
119308

120309
#### Go
121310

122311
```go
123-
312+
type Hashing struct {
313+
p []int64
314+
h []int64
315+
mod int64
316+
}
317+
318+
func NewHashing(word string, base int64, mod int64) *Hashing {
319+
n := len(word)
320+
p := make([]int64, n+1)
321+
h := make([]int64, n+1)
322+
p[0] = 1
323+
for i := 1; i <= n; i++ {
324+
p[i] = (p[i-1] * base) % mod
325+
h[i] = (h[i-1]*base + int64(word[i-1])) % mod
326+
}
327+
return &Hashing{p, h, mod}
328+
}
329+
330+
func (hashing *Hashing) Query(l, r int) int64 {
331+
return (hashing.h[r] - hashing.h[l-1]*hashing.p[r-l+1]%hashing.mod + hashing.mod) % hashing.mod
332+
}
333+
334+
func minValidStrings(words []string, target string) (ans int) {
335+
base, mod := int64(13331), int64(998244353)
336+
hashing := NewHashing(target, base, mod)
337+
338+
m, n := 0, len(target)
339+
for _, w := range words {
340+
m = max(m, len(w))
341+
}
342+
343+
s := make([]map[int64]bool, m+1)
344+
345+
f := func(i int) int {
346+
l, r := 0, int(math.Min(float64(n-i), float64(m)))
347+
for l < r {
348+
mid := (l + r + 1) >> 1
349+
sub := hashing.Query(i+1, i+mid)
350+
if s[mid][sub] {
351+
l = mid
352+
} else {
353+
r = mid - 1
354+
}
355+
}
356+
return l
357+
}
358+
359+
for _, w := range words {
360+
h := int64(0)
361+
for j := 0; j < len(w); j++ {
362+
h = (h*base + int64(w[j])) % mod
363+
if s[j+1] == nil {
364+
s[j+1] = make(map[int64]bool)
365+
}
366+
s[j+1][h] = true
367+
}
368+
}
369+
370+
var last, mx int
371+
372+
for i := 0; i < n; i++ {
373+
dist := f(i)
374+
mx = max(mx, i+dist)
375+
if i == last {
376+
if i == mx {
377+
return -1
378+
}
379+
last = mx
380+
ans++
381+
}
382+
}
383+
return ans
384+
}
124385
```
125386

126387
<!-- tabs:end -->

0 commit comments

Comments
(0)

AltStyle によって変換されたページ (->オリジナル) /