I
Vettori sono delle Strutture Dati utilizzabili nei Linguaggi di Programmazione evoluti. Una Struttura Dati è uno strumento Concettuale utile per memorizzare Informazioni secondo una certa logica e disposizione. Nel Vettore si possono memorizzare più informazioni dello stesso tipo in adiacenza fisica, e cioè una vicina all'altra. Il vettore è formato da Elementi in cui sono memorizzate le informazioni, una per ogni elemento, e si può considerare come una variabile multipla.
Ad ogni Vettore viene sempre associato un
Nome Simbolico - come per le variabili semplici - e per distinguere i vari elementi fra di loro viene utilizzato un Indice. L'Indice è sostanzialmente un numero intero rappresentato da una costante, da una variabile o da un'espressione, che segue, fra parentesi quadre in Pascal, tonde in Basic, il Nome del Vettore. Normalmente il primo elemento di un Vettore è identificato da un valore di Indice pari ad 1, il secondo da 2, il terzo da tre ecc.
Di seguito viene riportato un esempio di definizione di Vettore in Pascal e uno in Basic:

Var
    Numeri : Array[1 .. 100] of Integer;

La dichiarazione precedente, in Pascal, serve per definire un Vettore di 100 elementi  in cui il primo elemento viene identificato da un valore di Indice pari ad 1.  Il nome del Vettore è Numeri.
Per impostare nel terzo elemento di Numeri un certo valore, ad esempio 10, si può utilizzare l'assegnazione seguente:

Numeri[3] := 10; 

oppure

I := 3;
Numeri[I] := 10;

In Basic lo stesso Vettore lo si può definire in questo modo:

Dim Numeri( 1 to 100) as Integer

o anche con

Dim Numeri(99) as Integer

in quest'ultimo caso il primo elemento sarà identificato da un valore di Indice pari a 0.

Come si è visto occorre definire il numero massimo di elementi utilizzabili per il vettore.
Normalmente si usano gli elementi, a partire dal primo, in sequenza, senza lasciare vuoti. Cercare di utilizzare un elemento con un indice superiore al valore di indice massimo provoca un errore in fase di esecuzione, con interruzione del programma.
Per ricordare quanti elementi sono stati effettivamente impostati in un vettore, si utilizza una variabile intera in cui si memorizza il valore di indice dell'ultimo elemento impostato.

Il Vettore  permette di memorizzare insiemi di valori utilizzando un unico nome simbolico. Con i cicli,  facendo variare il valore dell'indice, è possibile operare su tutti gli elementi di un vettore. Come esempio viene riportato un Flow in cui, mediante un ciclo While, vengono visualizzati i primi N valori presenti in un vettore di nome Vet (viene utilizzata la variabile I come indice del vettore):

    
Vet1.gif (3852 byte)

In Pascal:

-----------------
I := 1;
While I <= N do
     begin
              Writeln(Vet[I]);
              I := I + 1;
      end;

Il ciclo For poteva, in questo caso, essere convenientemente utilizzato al posto del ciclo While.
Il ciclo For è utilissimo per operare sui vettori. La variabile di controllo del ciclo For può anche servire come indice del vettore per indicare, ad ogni ripetizione, un suo elemento diverso.

Vet2.gif (2767 byte)

In Pascal

-------------
For I := 1 to N do
      Writeln(Vet[I]);

Per impostare più valori in un vettore, a partire dal primo elemento, si possono utilizzare due strategie: 

1)  Impostare in Input il numero degli elementi da inserire, e successivamente inserire all'interno di un ciclo For gli elementi, uno alla volta:

Vet3.gif (5159 byte)

In Pascal

Program Carica1;
Uses Wincrt;
Var
         Vet: Array[1..100] of integer;
          I,N:integer;
begin
         Writeln(' Quanti elementi da inserire ? ');
          Readln(N);
          For I := 1 to N do
                  begin
                        Writeln(' Inserire l''elemento n. ',I);
                        Readln(Vet[I]);
                   end;
            -------------

end.

2)  Inserire un elemento alla volta chiedendo all' operatore se c'è un altro elemento da inserire:

Vet4.gif (6161 byte)

In Pascal

Program Carica2;
Uses Wincrt;
Var
         Vet:Array[1..100] of integer;
          N:integer;
          Risp:char;
begin
         N := 0;
         Repeat
                N := N + 1;
                Writeln('Inserire il valore n. ',N);
                Readln(Vet[N);
                Write('Vuoi continuare ? (S/N) -> ');
                Readln(Risp);
          Until (Risp = 'N') or (Risp = 'n');
          ----------------

end.

Le due strategie portano allo stesso risultato, ovviamente la prima prevede che vengano contati a priori i valori da inserire ed è comoda quando gli elementi del vettore sono pochi, o quando si sa con precisione quanti sono; la seconda ha come onere, da parte dell'operatore, la risposta alla domanda "Vuoi continuare ? (s/n)", ma non prevede che vengano contati, a priori, i valori da inserire.  Si sceglierà, quindi, il metodo più conveniente, a seconda delle esigenze.

Vediamo ora come si può ricercare un valore specifico all'interno di un vettore precedentemente impostato.
Esistono sostanzialmente tre metodi:

RICERCA SERIALE (non prevede che i valori siano in una sequenza crescente)

RICERCA SEQUENZIALE (prevede che i valori siano in una sequenza crescente)

RICERCA DICOTOMICA (prevede che i valori siano in una sequenza crescente)

Vediamo ora la RICERCA SERIALE:

I valori utili sono stati impostati nel vettore VET a partire dal primo elemento, senza lasciare elementi vuoti. La variabile di comodo N sarà stata impostata con un valore numerico intero, ad indicare quanti valori sono stati impostati nel vettore (VET e N sono due nomi simbolici utilizzati per spiegare il procedimento).
La ricerca di uno specifico valore, con il metodo seriale, prevede che venga preso in considerazione il valore presente nel primo elemento del vettore e via via gli altri valori negli elementi sucessivi, ovviamente uno alla volta. La ricerca terminerà con esito positivo se il valore cercato verrà trovato, o con esito negativo se, dopo aver preso in considerazione gli N elementi del vettore, non si sarà trovato alcun valore corrispondente a quello cercato.
Il numero di elementi che verranno presi in considerazione (si possono anche equiparare ai numeri di passi necessari) in caso di esito negativo, cioè per
non trovato, saranno N, mentre in caso di esito positivo, cioè per trovato, saranno in media N/2, poichè l'elemento cercato, se presente, può trovarsi ovunque nel vettore. 
   

Vet5.gif (9153 byte)

La variabile Flag è una variabile di comodo che serve per uscire dal ciclo While non appena viene individuato il valore cercato. La stessa variabile servirà come indicatore del fatto che il valore è stato trovato (valore 1 impostato nel ramo "vero" del confronto X = Vet(I))

In Pascal

Writeln('Inserire il valore da cercare');
Readln(X);
I := 0;
Flag := 0;
While (Flag=0) And (I<=N) do
       if (X = Vet[I]) then
              Flag := 1
       else
              I := I + 1;
if Flag = 1 then
       Writeln('Trovato')
else
        Writeln('NON Trovato');
 

Vediamo ora la RICERCA SEQUENZIALE:

La ricerca sequenziale è molto simile alla ricerca seriale e si differenzia da questa solo per il fatto che, essendo i valori nel vettore in ordine crescente, il confronto con gli elementi può anche terminare non appena viene individuato un valore più grande di quello che si cerca. L'ordinamento crescente prevede che sia vera questa situazione: Vet(1) <= Vet(2) <= Vet(3) <= ...... <= Vet(N). Dopo aver individuato un elemento più grande di quello che si cerca, si è nella situazione di non dovere più esaminare i successivi elementi, tutti più grandi ancora.
Il numero di passi per
trovato non cambia ed è sempre N/2; cambia invece il numero di passi per non trovato, che si può ritenere, in media, pari a N/2. Questo perchè non è necessario esaminare tutti gli elementi (normalmente) per essere certi della inesistenza del valore cercato.

Vet6.gif (10783 byte)

In Pascal

Writeln('Inserire il valore da cercare');
Readln(X);
I := 0;
Flag := 0;
While (Flag=0) And (I<=N) do
       if (X = Vet[I]) then
              Flag := 1
       else
              if (Vet[I] > X) then
                    Flag := 2
              else
                    I := I + 1;
if Flag = 1 then
       Writeln('Trovato')
else
        Writeln('NON Trovato');
 

Vediamo ora la RICERCA DICOTOMICA:

Dicotomia è una parola che deriva dal Greco antico e indica una separazione, in due parti, di un qualche oggetto o cosa. In informatica " Ricerca Dicotomica" indica un procedimento che serve per individuare un valore in un insieme ordinato (nel nostro caso, al momento, un vettore) procedendo per esclusione di metà degli elementi: la prima parte dell'insieme, o la seconda parte, a seconda che il valore da cercare sia minore di quello presente a metà dell'insieme, oppure sia maggiore. Si procederà, nuovamente per esclusione, con la parte di insieme individuato nel passaggio precedente, riducendo nuovamente, con lo stesso procedimento, gli elementi in cui cercare. La ricerca terminerà, per trovato, se verrà individuato il valore cercato in uno dei confronti operati per individuare la parte di insieme in cui cercare (prima di confrontare per maggiore si confronterà per uguale), o per non trovato se l'insieme in cui cercare si sarà ridotto ad un elemento, e poi a nessun elemento. Il numero di passi necessari per individuare un valore con questo procedimento non segue più una legge lineare, come per i due metodi precedentemente presentati, ma la legge seguita è di tipo logaritmico. Infatti se i valori sono N, dopo un passo si ridurranno di N/2, dopo due passi di N/4 ... ; quando il numero di elementi rimasti si ridurrà a 1, la ricerca terminerà per non trovato, oppure per trovato nella peggiore ipotesi. Il numero di passi sarà, quindi, quante volte abbiamo dovuto dividere l'insieme di ricerca per ottenere un unico valore. Questo numero è, per definizione matematica, il Logaritmo in base due di N, e cioè quel numero che messo come esponente a due permette di ottenere N. Se gli elementi in cui cercare sono, ad esempio, 1024 dopo un passo si ridurranno a 512, dopo 2 passi a 256, dopo 3 a 128 ... dopo 10 a 1.Dieci, nel caso precedente, è il numero di passi necessari per non trovato o per trovato nella peggiore delle ipotesi, ed è appunto il logaritmo in base 2 di 1024. La ricerca sequenziale o la seriale avrebbero richiesto N/2 passi o elementi e cioè circa 500 passi. Si può osservare come i numeri dicano quanto possa essere più veloce la ricerca di tipo dicotomico, specialmente quando gli elementi in cui cercare sono molti. Si può notare, inoltre, che raddoppiando gli elementi il numero di passi aumenta solo di uno. La ricerca dicotomica è in pratica quella che ognuno di noi, almeno in modo empirico, mette in atto quando cerca un nominativo in un elenco telefonico o  quando cerca un termine in un dizionario. In Informatica questo tipo di ricerca assume un'importanza fondamentale, visto il ridottissimo numero di passi richiesto rispetto agli altri metodi. Ovviamente questo tipo di ricerca non può essere effettuata se i valori nell'insieme di ricerca non sono ordinati.   

Vet7.gif (12231 byte)

 

In Pascal

Writeln('Inserire il valore da cercare');
Readln(X);
Inizio := 1;
Fine := N;
Flag := 0;
While (Inizio <= Fine) And (Flag = 0) do
       begin
              Med := (Inizio + Fine) Div 2;
              if (X = Vet[Med]) then
                       Flag := 1
              else
                     if (X > Vet[Med]) then
                            Inizio := Med +1
                    else
                           Fine := Med - 1;
         end;
if Flag = 1 then
       Writeln('Trovato')
else
        Writeln('NON Trovato');