Editorial for COCI '15 Contest 5 #6 Podnizovi


Remember to use this editorial only when stuck, and not to copy-paste code from it. Please be respectful to the problem author and editorialist.
Submitting an official solution before solving the problem yourself is a bannable offence.

Let's first observe the following algorithm:

S = {} // current set of subarrays

for i in {1..K}
    x = lexicographically smallest subarray from S
    s.remove(x)
    print hash(x)
    for y in {subarrays created by adding one element to the end of x}
        s.add(x)

Therefore, we iterate over subarrays ascending lexicographically and after we process a subarray we add all subarrays created from it into the processing set.

We will make a series of optimizations of the given algorithm. Let's define the children of the subarray as all the subarrays created by adding one element to the end of the current subarray.

  1. Notice that there is no need to add more than one child of a subarray into the set. Only when we process a child, do we add the next lexicographical child of a subarray into the set.
  2. When we are searching for the next smallest lexicographical child of a subarray, we can do this quickly by using a Fenwick tree or a tournament tree.
  3. The comparison of subarrays from the set can be done quickly if we compare prefixes of the size 2^k.

The time complexity of the algorithm is \mathcal O(N \log^2 N).

An alternative solution uses a recursive processing of subarrays, which results in somewhat simpler code.


Comments

There are no comments at the moment.