Разбор
Пусть массив хранит идентификационные номера песен. С помощью двух указателей будем поддерживать скользящее окно , в котором песни не повторяются. Иными словами, на отрезке все песни уникальны. Песни из этого отрезка будем хранить во множестве . Для каждого значения будем стремиться расширить отрезок до максимальной возможной длины. То есть для фиксированного будем искать такое , что на отрезке песни не повторяются, а на отрезке уже появляются дубли.
При обработке текущей песни с индексом имеются два варианта:
если песня не встречается в отрезке , то добавляем ее в этот отрезок, расширяя его до ;
если песня уже присутствует в отрезке, сдвигаем левую границу вправо до тех пор, пока не исчезнет из отрезка . Затем добавляем в отрезок, расширяя его до . При каждом сдвиге удаляем соответствующие элементы из множества ;
Среди всех возможных отрезков с уникальными песнями находим максимальную длину. Это и будет ответом на задачу.
Пример
Рассмотрим как будут изменяться отрезки с неповторяющимися песнями для первого примера.
Длина наибольшего отрезка равна .
Реализация алгоритма
Читаем входные данные. Идентификационные номера песен храним в массиве .
scanf("%d", &n); v.resize(n); for (i = 0; i < n; i++) scanf("%d", &v[i]);
Поддерживаем отрезок из неповторяющихся песен (то есть песни от до не повторяются). Во множестве храним идентификационные номера песен из этого отрезка. В переменной отслеживаем длину самого длинного фрагмента с уникальными песнями.
i = res = 0; for (j = 0; j < n; j++) {
Рассматриваем текущую песню с индексом . Если она уже содержится во множестве , то расширить текущий отрезок за счет -ой песни не удастся. В этом случае необходимо сдвигать левую границу , удаляя из множества песню , до тех пор, пока -ая песня не исчезнет из множества .
while (s.find(v[j]) != s.end()) { s.erase(v[i]); i++; }
Добавим -ую песню в отрезок и, соответственно, во множество . Таким образом, отрезок не будет содержать повторяющихся песен.
s.insert(v[j]);
Среди всех возможных отрезков находим самый длинный. Длина отрезка равна .
res = max(res, j - i + 1); }
Выводим ответ.
printf("%d\n", res);