Первая мысль. Вы можете определить длину n
строки в O(log2(n))
.
- Проверка
Z*
, где Z
представляет k
вопросительные знаки, начиная с 0, затем 1, а затем удваивая количество вопросительных знаков при каждой проверке, пока не будет найдено совпадение. n
должно быть между k / 2
и k
- Найти точную длину, используя тот же шаблон, изменяющий
k
так же, как это делает бинарный поиск.
Знание точной длины может помочь выполнить своего рода «разделяй и властвуй» в пространственной области.
UPDATE
Если вы знаете длину, вы можете использовать тот же шаблон, чтобы правильно найти символ.
* +1025 * Пример:
..X. ..XX (spaces added for readability)
+ symbol may be X
- symbol is not X
X symbol is X
*X* => MATCH ++++ ++++
*X* ???? => MATCH ++++ ++++
*X*?? ???? => NO MATCH --++ ++++
??X? ???? => MATCH --X+ ++++
??XX ???? => NO MATCH --X- ++++
??X? *X*?? => NO MATCH --X- --++
??X? ??X? => MATCH --X- --X+
??X? ??XX => MATCH --X- --XX
Для длины строки n
и размера алфавита m
это займет около O(log2(n))
, чтобы найти длину строки, около O(n • log2(n))
, чтобы правильно разместить n
символов, и O(m)
, чтобы найти используемые символы - суммируя все вместе, получаем O(n • log2(n) + m)
.
Я мог бы предположить, что это можно ускорить, объединив несколько шагов - возможно, проверьте используемые символы при определении длины строки или одновременно обнаружив два (или даже больше?) Символа в первой и второй половине строки. Это потребует повторной проверки объединенных шагов в случае неудачной проверки, чтобы определить, какая проверка не удалась. Но до тех пор, пока объединенная проверка завершится успешно, вы получите информацию об обоих.
Может быть, я вычислю это завтра, чтобы посмотреть, действительно ли это ускорит процесс.