{ File: vettsupp.pas }

program VettoriSupporto;
{ Vengono letti da input due vettori di AL PIU' N componenti intere <> 0.
  Si assume che l'utente scriva i valori uno dopo l'altro, sulla stessa riga,
  terminando la sequenza con uno zero. Se l'utente fornisce piu' di N valori,
  solo i primi N vengono immessi nel vettore.
  Dopo la lettura si effettua una stampa di controllo
  e poi viene calcolato e stampato il vettore somma.
}

const
  N = 8;

{ Specifica di struttura dati:
  in un vettore una componente e' "significativa" se e' stata
  immessa dall'utente nel corso dell'ultima lettura.
  Il formato di un vettore V sara' pertanto il seguente:

  prima componente = V[1]
   = numero di interi significativi nel vettore;

  componenti dalla seconda in poi
   = interi memorizzati nel vettore (dei quali i primi V[1] sono significativi)

  La sequenza degli interi significativi in V corrisponde pertanto a
    V[2], V[3], ..., V[ V[1]+1 ]
}


type
  TipoVettSupp = array [1..N+1] of integer;
  { N componenti per gli al piu' N interi significativi, piu' una per la loro
    effettiva quantita' nel vettore }

var
  v1, v2,                   { i vettori letti da input }
  v3     : TipoVettSupp;    { il vettore somma }


  procedure LeggiVettSupp (var v:TipoVettSupp);
  { Legge una sequenza di al piu' N interi da input e li memorizza in V.
    Dopo la lettura, V[1] contiene il numero di interi che sono stati forniti
    da input.  L'utente termina con 0 la sequenza di input.}

  var
    i      : integer;      { contatore per scandire il vettore }
    ins0   : boolean;      { segnala se l'utente ha inserito uno 0 }
    numero : integer;      { per leggere i numeri in input - ridondante ...- }

  begin { LeggiVettSupp }
    { Algoritmo:
      inizializzazione i := 2 (prima componente da riempire con interi)
                       ins0 := FALSE (nessuno zero ancora)
      mentre <si puo' inserire un numero>
        1) lettura numero
        2) se numero = 0
             allora
               ins0 := TRUE
             altrimenti
               - assegnazione V[i] con numero
               - incremento di i (per la prossima lettura)

           <si puo' inserire un numero> equivale a dire
           che <ci sono ancora componenti nel vettore> = (i<=N+1)
               E
               <non e' stato dato 0 in input> = (ins0=false) = not(ins0)

        3) all'uscita dal ciclo una di queste due condizioni non vale:
           se ins0 = TRUE
              allora abbiamo inserito i-1 interi
              altrimenti ne abbiamo inseriti N (esaurendo lo spazio)
     }

    i := 2;
    ins0 := FALSE;

    while (not ins0) and (i <= N+1) do
    begin
      read(numero);

      if numero = 0 then
        ins0 := TRUE
      else
      begin
        v[i] := numero;
        i := i+1
      end
    end;
    readln; { passa sulla prossima linea di input }

    if ins0 then
      v[1] := i-2
    else
      v[1] := N
  end; { LeggiVettSupp }


  procedure StampaVettSupp (v: TipoVettSupp);
  { Stampa il vettore V.
    Output su due righe: una con gli indici del vettore e l'altra con i valori
    relativi.
    NB: le componenti effettive del vettore sono N+1. }

  var
    i : integer;      { contatore per scandire il vettore }

  begin {StampaVettSupp }
    write(' indice ');
    write('|', 1:3, ' | ');     { stampa primo indice }
    for i := 2 to N+1 do        { stampa numeri di indice }
      write(i:3, ' ');

    writeln;

    write(' valore ');
    write('|', v[1]:3, ' | ');  { stampa prima componente }
    for i := 2 to N+1 do        { stampa componenti del vettore }
      if i <= v[1]+1 then
        write(v[i]:3, ' ')
      else
        write('  - ');
  end; { StampaVettSupp }


  procedure SommaVettSupp (a, b: TipoVettSupp; var c:TIPOVETTSUPP);
  { Riempie il vettore C con la somma di A e B,
    tenendo conto del fatto che A[1] e B[1] dicono quante sono le
    componenti significative nei vettori da sommare. }

  var
    i : integer;      { contatore }

  begin { SommaVettSupp }
    if a[1] > b[1] then { il primo vettore ha piu' componenti significative }
    begin
      c[1] := a[1];   { assegnazione numero di componenti significative per C }

      { somma sugli indici di componenti significative sia per A che per B }
      for i := 2 to b[1]+1 do
        c[i] := a[i] + b[i];

      { copia in C delle componenti che erano significative solo per A }
      for i := b[1] + 2 to a[1]+1 do
        c[i] := a[i]
    end
    else { il secondo vettore ha piu' componenti significative }
    begin
      c[1] := b[1];   { assegnazione numero di componenti significative per C }

      { somma sugli indici di componenti significative sia per A che per B }
      for i := 2 to A[1]+1 do
        c[i] := a[i] + b[i];

      { copia in C delle componenti che erano significative solo per B }
      for i := a[1]+2 to b[1]+1 do
        c[i] := b[i]
    end
  end; { SommaVettSupp }


begin { VettoriSupporto }
  writeln(' -- lettura primo vettore   --');
  LeggiVettSupp(v1);
  writeln(' -- lettura secondo vettore --');
  LeggiVettSupp(v2);
  writeln;
  writeln(' -- stampe di controllo     --');
  writeln(' -----------------------------');
  writeln(' -- primo vettore:          --');
  StampaVettSupp(v1);
  writeln;
  writeln(' -----------------------------');
  writeln(' -- secondo vettore:        --');
  StampaVettSupp(v2);
  writeln;
  writeln(' -----------------------------');
  writeln(' -- vettore somma:          --');
  SommaVettSupp(v1, v2, v3);
  StampaVettSupp(v3);
  writeln;

{ writeln('<RET> per finire.');
  readln }
end. { VettoriSupporto }