program wp08zad3;

const
    MAX_ZNAK = 255;

type
    Konteksty = ^Wezel;
    Wezel = record
        koncowy : Char;
        ile : Integer;
        nastepne : array [Char] of Konteksty;
        znaki : array [0 .. MAX_ZNAK] of Char;
        slad, kolejny : Konteksty
    end;

var aktualny, lista, graf, drzewo, akt, w : Konteksty;
    i, rzad, ograniczenie : Longint;
    kodBledu : Word;
    c, znak : Char;

function nowyWezel : konteksty;
var pom : Konteksty;
    c : Char;
begin
    new(pom);
    pom^.koncowy := chr(0);
    pom^.ile := 0;
    for c := chr(0) to chr(MAX_ZNAK) do
        pom^.nastepne[c] := nil;
    pom^.slad := nil;
    pom^.kolejny := lista;
    lista := pom;
    nowyWezel := pom
end;

begin
    randomize;
    if (paramcount <> 2) then begin
        writeln('Program oczekuje dwoch argumentow');
        halt
    end;
    rzad := 0;
    val(paramstr(1), rzad, kodBledu);
    if (kodBledu <> 0) or (rzad < 0) then begin
        writeln('Dlugosc kontekstu powinna byc nieujemna liczba calkowita');
        halt
    end;
    ograniczenie := 0;
    val(paramstr(2), ograniczenie, kodBledu);
    if (kodBledu <> 0) or (ograniczenie < 0) then begin
        writeln('Ograniczenie powinno byc nieujemna liczba calkowita');
        halt
    end;
    lista := nil;
    graf := nowyWezel;
    graf^.slad := graf;
    drzewo := nowyWezel;
    aktualny := graf;
    while not eof do begin
        read(znak);
        if aktualny^.nastepne[znak] = nil then begin
            w := drzewo;
            akt := aktualny;
            c := znak;
            for i := 1 to rzad do begin
                if w^.nastepne[c] = nil then
                    w^.nastepne[c] := nowyWezel;
                w := w^.nastepne[c];
                c := akt^.koncowy;
                akt := akt^.slad
            end;
            w^.slad := aktualny;
            w^.koncowy := znak;
            aktualny^.nastepne[znak] := w;
            aktualny^.znaki[aktualny^.ile] := znak;
            aktualny^.ile := aktualny^.ile + 1
        end;
        aktualny := aktualny^.nastepne[znak]
    end;
    aktualny := graf;
    while (aktualny^.ile <> 0) and (ograniczenie > 0) do begin
        znak := aktualny^.znaki[random(aktualny^.ile)];
        write(znak);
        ograniczenie := ograniczenie - 1;
        aktualny := aktualny^.nastepne[znak]
    end;
    while lista <> nil do begin
        aktualny := lista;
        lista := lista^.kolejny;
        dispose(aktualny)
    end
end.
