Skip to content

Commit b4c890f

Browse files
Merge pull request #193
add new problems 13.05
2 parents ccfcab7 + 8f39780 commit b4c890f

File tree

6 files changed

+205
-17
lines changed

6 files changed

+205
-17
lines changed
Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,17 @@
11
package com.github.contest
22

3-
fun MutableMap<Int, Int>.removeIfEmptyBucket(key: Int) {
4-
this[key] = this.getOrDefault(key, 0) - 1
3+
4+
fun <K, V> MutableMap<K, V>.removeIfEmptyBucket(key: K) {
55
if (this[key] == 0) this.remove(key)
66
}
77

8-
9-
fun Any.printData(label: String) {
10-
println("$label $this")
8+
fun <K> MutableMap<K, Int>.reduceCount(key: K) {
9+
this[key] = this.getOrDefault(key, 0) - 1
10+
removeIfEmptyBucket(key)
1111
}
1212

1313

14-
inline fun abs(number: Int): Int = when {
14+
fun abs(number: Int): Int = when {
1515
number < 0 -> number * -1
1616
else -> number
1717
}

contest/src/main/java/com/github/contest/Execute.kt

Lines changed: 37 additions & 9 deletions
Large diffs are not rendered by default.

contest/src/main/java/com/github/contest/priorityqueue/PriorityQueueProdVariant.kt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,13 +6,13 @@ package com.github.contest.priorityqueue
66

77
fun topKFrequentProdVariant(nums: IntArray, k: Int): IntArray {
88
val freq = mutableMapOf<Int, Int>()
9-
val repeated = Array<MutableList<Int>>(nums.size + 1) {mutableListOf()}
9+
val repeated = Array<MutableList<Int>>(nums.size + 1) { mutableListOf() }
1010

1111
for (num in nums) freq[num] = freq.getOrDefault(num, 0) + 1
1212

1313
for ((num, count) in freq) {
1414
repeated[count].add(num)
1515
}
1616

17-
return repeated.flatMap {it}.takeLast(k).toIntArray()
17+
return repeated.flatMap { it }.takeLast(k).toIntArray()
1818
}

contest/src/main/java/com/github/contest/slidingWindow/SlidingWindowLeetcode.kt

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -300,4 +300,23 @@ fun minimumSumSubarray(nums: List<Int>, l: Int, r: Int): Int {
300300
return TODO("Make this method")
301301
}
302302

303+
/**
304+
* 187. Repeated DNA Sequences
305+
*/
306+
307+
fun findRepeatedDnaSequences(s: String): List<String> {
308+
if (s.length < 10) return listOf()
309+
310+
val dnas = s.windowed(10).map { it }.groupingBy { it }.eachCount()
311+
val res = mutableListOf<String>()
312+
313+
for ((key, value) in dnas) {
314+
if (value > 1) res.add(key)
315+
}
316+
317+
318+
return res
319+
}
320+
321+
303322

contest/src/main/java/com/github/contest/slidingWindow/SlidingWindowProdVariant.kt

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -96,3 +96,17 @@ fun minimumSumSubarrayProdVariant(nums: List<Int>, l: Int, r: Int): Int = buildL
9696
nums.windowed(window).map { it.sum() }.filter { it > 0 }.forEach { add(it) }
9797
}
9898
}.minOrNull() ?: -1
99+
100+
/**
101+
* 187. Repeated DNA Sequences
102+
* Prod Variant
103+
*/
104+
105+
fun findRepeatedDnaSequencesProdVariant(s: String): List<String> = when {
106+
s.length < 10 -> listOf()
107+
else -> buildList {
108+
s.windowed(10).map { it }.groupingBy { it }.eachCount().forEach { (key, value) ->
109+
if (value > 1) add(key)
110+
}
111+
}
112+
}
Lines changed: 127 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,127 @@
1+
package com.github.contest.slidingWindow.customStructure
2+
3+
4+
fun rabinKarpSearch(text: String, pattern: String): List<Int> {
5+
val d = 256 // Размер алфавита (ASCII)
6+
val q = 101 // Простое число для избежания переполнения
7+
val m = pattern.length
8+
val n = text.length
9+
var patternHash = 0 // Хеш образца
10+
var textHash = 0 // Хеш текущего окна в тексте
11+
var h = 1 // Значение для "скользящего" хеша: h = d^(m-1)
12+
val result = mutableListOf<Int>()
13+
14+
if (n < m || m == 0 || n == 0) return result
15+
16+
// Вычисляем h = d^(m-1) % q
17+
for (i in 0 until m - 1) {
18+
h = (h * d) % q
19+
}
20+
21+
// Вычисляем начальные хеши для образца и первого окна текста
22+
for (i in 0 until m) {
23+
patternHash = (d * patternHash + pattern[i].code) % q
24+
textHash = (d * textHash + text[i].code) % q
25+
}
26+
27+
// Проходим по тексту
28+
for (i in 0..n - m) {
29+
// Если хеши совпали, проверяем символы один за другим
30+
if (patternHash == textHash) {
31+
var match = true
32+
for (j in 0 until m) {
33+
if (text[i + j] != pattern[j]) {
34+
match = false
35+
break
36+
}
37+
}
38+
if (match) {
39+
result.add(i)
40+
}
41+
}
42+
43+
// Вычисляем хеш для следующего окна текста
44+
if (i < n - m) {
45+
textHash = (d * (textHash - text[i].code * h) + text[i + m].code) % q
46+
// Обеспечиваем положительное значение хеша
47+
if (textHash < 0) textHash += q
48+
}
49+
}
50+
51+
return result
52+
}
53+
54+
fun rabinKarpMultiPattern(text: String, patterns: List<String>): Map<String, List<Int>> {
55+
val d = 256
56+
val q = 101
57+
val result = mutableMapOf<String, MutableList<Int>>()
58+
val patternHashes = mutableMapOf<Int, MutableList<String>>()
59+
60+
// Предварительно вычисляем хеши всех образцов
61+
for (pattern in patterns.distinct()) {
62+
val m = pattern.length
63+
if (m == 0 || m > text.length) continue
64+
65+
var hash = 0
66+
for (i in 0 until m) {
67+
hash = (d * hash + pattern[i].code) % q
68+
}
69+
70+
patternHashes.getOrPut(hash) { mutableListOf() }.add(pattern)
71+
result[pattern] = mutableListOf()
72+
}
73+
74+
// Ищем все возможные длины образцов
75+
val lengths = patterns.map { it.length }.distinct().sorted()
76+
77+
for (m in lengths) {
78+
if (m == 0 || m > text.length) continue
79+
80+
var h = 1
81+
for (i in 0 until m - 1) {
82+
h = (h * d) % q
83+
}
84+
85+
var textHash = 0
86+
// Вычисляем хеш первого окна
87+
for (i in 0 until m) {
88+
textHash = (d * textHash + text[i].code) % q
89+
}
90+
91+
// Проверяем первый хеш
92+
patternHashes[textHash]?.forEach { pattern ->
93+
if (pattern.length == m && text.startsWith(pattern, 0)) {
94+
result[pattern]?.add(0)
95+
}
96+
}
97+
98+
// Скользим по тексту
99+
for (i in 1..text.length - m) {
100+
// Обновляем хеш
101+
textHash = (d * (textHash - text[i - 1].code * h) + text[i + m - 1].code) % q
102+
if (textHash < 0) textHash += q
103+
104+
// Проверяем совпадения
105+
patternHashes[textHash]?.forEach { pattern ->
106+
if (pattern.length == m && text.startsWith(pattern, i)) {
107+
result[pattern]?.add(i)
108+
}
109+
}
110+
}
111+
}
112+
113+
return result
114+
}
115+
116+
fun slidingWindowClassic(text: String, patterns: List<String>): List<Int> {
117+
val res = mutableListOf<Int>()
118+
119+
for (pattern in patterns) {
120+
val window = pattern.length
121+
text.windowed(window) {
122+
if (it == pattern) res.add(0)
123+
}
124+
}
125+
126+
return res
127+
}

0 commit comments

Comments
 (0)