Editorial for IOI '96 P5 - Longest Prefix
Submitting an official solution before solving the problem yourself is a bannable offence.
Let be a sequence of letters and let
be a set of primitives. Denote by
the set of sequences
such that the following two conditions hold:
is a prefix of a primitive in
.
for some
. (For two sequences of letters
and
, we denote the concatenation of
and
by
.)
It is obvious that can be composed from primitives in
iff the empty sequence is in
. Moreover,
has an extension
on the right that makes
a composition of primitives in
iff
is non-empty. Therefore the following algorithm gives a solution to the task if DataFile contains the sequence to be examined.
Res:=0;
S:=empty; NoS:=1;
ReadLn(DataFile,X);
Slength:=1;
While (X<>'.') And (NoS>0) Do Begin
Append X to the end of S;
Q:=Suff(S,P);
NoS:=number of elements of Q;
If the empty sequence is element of Q Then Res:=Slength;
ReadLn(DataFile,X);
Inc(Slength);
End;
WriteOut(Res);
One obvious problem with this algorithm is that the data file is too large to read into the memory (unless you know how to use the machine's extra memory).
Fortunately, it is not necessary to read the whole sequence into memory. Let us observe that for a sequence
and a letter
can be computed from the set
. Indeed, the following algorithm satisfies the requirement that if
holds before executing
then after the execution
will hold.
Procedure Next(Q,X);
Begin
Q1:=empty;
Forall u in Q Do Begin
If ux is a prefix of some primitives in P Then
Begin
include ux in Q1;
If ux is equal to a primitive in P
Then include the empty sequence in Q1
End;
End;
Q:=Q1;
End;
In order to refine the algorithm , we have to answer the questions:
- Is a sequence
a prefix of some primitive in
?
- Is a sequence
equal to a primitive in
?
Consider the following data structure for the set of primitives .
Const
MaxN=100; (* maximum possible number of primitives *)
MaxL=20; (* maximum possible length of primitives *)
Var
P:Array[1..MaxN,1..MaxL] Of Char; (* array of primitives *)
L:Array[1..MaxN] Of Word; (* length of the primitives *)
Let us represent a sequence which is a prefix of a primitive in
by the pair
, such that the prefix of
consisting of the first
letters of the primitive
equals
, and
is the least such index for
. Note that the empty sequence is represented by the pair
.
We can preprocess the set of primitives to build a transition table :
is
if there is no primitive in
with prefix
, otherwise the least index
such that
is a prefix of
. (
denotes the sequence of letters consisting of the first
elements of the primitive
.)
In other words, if a sequence is represented by the pair
then the sequence
is a prefix of a primitive in
iff
, and in this case
is a prefix of
and is represented by the pair
. A procedure computes the transition table
and builds the array
as well.
is true iff the sequence represented by
is equal to a primitive in
.
We can easily implement the algorithm using the arrays
and
.
Comments