Недавно я дал интервью компании, занимающейся разработкой программного обеспечения. Мне задали вопрос о самой длинной уникальной подстроке в строке. Мои алгоритмы были следующими:Поиск самой длинной подстроки без повторения в строке. Сложность времени?
Начните с самого левого символа и сохраните символ в хеш-таблице с ключом как character
и значением как index_where_it_last_occurred
. Добавьте символ в строку ответа, пока его нет в хеш-таблице. Если мы снова столкнемся с сохраненным символом, я остановлю и запомню длину. Я очищаю хэш-таблицу, а затем начинаю снова с нужного индекса повторяющегося символа. Правильный индекс извлекается из флага (index_where_it_last_occurred). Если я когда-либо дойду до конца строки, я остановлюсь и вернусь к самой длинной длине.
Например, строка была, abcdecfg
.
Я начинаю с a
, хранить в хеш-таблице. Я магазин b
и т.д. до e
. Их индексы также хранятся. Когда я снова столкнулся с c
, я останавливаюсь, так как он уже хэширован и записывает длину, равную 5. Я опустошаю хэш-таблицу и начинаю с правого индекса повторяющегося символа. Повторяющийся символ c
, я начинаю снова с позиции 3, т. Е. Персонажа d
. Я продолжаю делать это, пока не дойду до конца строки.
Мне интересно узнать, какая временная сложность этого алгоритма будет. ИМО, это будет O (n^2).
Это код.
import java.util.*;
public class longest
{
static int longest_length = -1;
public static void main(String[] args)
{
Scanner in = new Scanner(System.in);
String str = in.nextLine();
calc(str,0);
System.out.println(longest_length);
}
public static void calc(String str,int index)
{
if(index >= str.length()) return;
int temp_length = 0;
LinkedHashMap<Character,Integer> map = new LinkedHashMap<Character,Integer>();
for (int i = index; i<str.length();i++)
{
if(!map.containsKey(str.charAt(i)))
{
map.put(str.charAt(i),i);
++temp_length;
}
else if(map.containsKey(str.charAt(i)))
{
if(longest_length < temp_length)
{
longest_length = temp_length;
}
int last_index = map.get(str.charAt(i));
// System.out.println(last_index);
calc(str,last_index+1);
break;
}
}
if(longest_length < temp_length)
longest_length = temp_length;
}
}
Вы уверены, что это проблема? Самая длинная уникальная подстрока будет всей строкой (она встречается только один раз). Если вы ограничены соответствующими подстроками, то почти во всех случаях вся строка без ее первого или последнего символа будет оптимальной. Единственный случай, когда это не выполняется, - это когда строка состоит из повторений одного символа: в этом случае нет уникальных собственных подстрок. –
Я думаю, вопрос заключается в поиске подстроки, в которой символ не появляется более одного раза.Я согласен, что это неясно. –
Это можно сделать в O (n) времени. Всякий раз, когда происходит повторение, не очищайте его полностью, просто сохраняйте длину и продвигайте левый указатель. – avmohan