Il linguaggio C Gli array I numeri casuali La direttiva DEFINE - Dichiarazione e memorizzazione di array L'inizializzazione di array La ...
←
→
Trascrizione del contenuto della pagina
Se il tuo browser non visualizza correttamente la pagina, ti preghiamo di leggere il contenuto della pagina quaggiù
Il linguaggio C
Gli array
Dichiarazione e memorizzazione di array
L’inizializzazione di array
La crittografia
Gli algoritmi di ordinamento
I numeri casuali C
L an
gu
ag
La direttiva DEFINE e
Fondamenti di Informatica I - a.a. 2020-21 1Gli array (vettori!)
Nel linguaggio C, un array è un insieme di variabili dello
stesso tipo memorizzate consecutivamente
Ogni variabile dell’array, detta elemento, può essere
acceduta mediante il nome dell’array ed un indice, con il
primo elemento individuato dall’indice di valore 0
Esempio: Memorizzare la temperatura media registrata
per ogni giorno dell’anno
Si dichiara un array di 365 elementi (piuttosto che 365
variabili!), identificati con un solo nome, e che occupano
posizioni di memoria consecutive
Nota: Gli array contengono informazione correlata (le
temperature di un anno, i voti di esame di uno studente,
etc.)
Fondamenti di Informatica I - a.a. 2020-21La dichiarazione di array - 1
La sintassi della dichiarazione di un array è:
Specificatore Nome Dimensione
di tipo dell’array
[ dell’array
]
=
La dichiarazione viene effettuata {inserendo
Valoriuna
iniziali coppia
} di
parentesi quadre dopo il nome dell’array
La dimensione dell’array viene specificata inserendo il
numero di elementi all’interno delle parentesi quadre
Fondamenti di Informatica I - a.a. 2020-21 3La dichiarazione di array - 2
Il riferimento ad un elemento dell’array è invece l’operazione
di accesso al dato elemento ed avviene utilizzando il nome
dell’array seguito dall’indice dell’elemento (racchiuso fra
parentesi quadre)
Le istruzioni di dichiarazione di un array e di riferimento ad un
elemento dell’array sono molto simili nella forma, ma molto
diverse nel significato
/* I seguenti sono riferimenti a elementi
/* La seguente è una dichiarazione; * dell’array; i valori 0,1,2,… specificano
* il valore 365 specifica il numero * gli elementi a cui accedere
* di elementi dell’array */
*/ daily_temp[0] = 2;
int daily_temp[365]; daily_temp[1] = 5;
daily_temp[2] = 3;
………
Fondamenti di Informatica I - a.a. 2020-21 4La dichiarazione di array - 3
Esempio: Calcolo della temperatura media annua
#include
#define DAYS_IN_YEAR 365
main()
{
int j, sum=0;
int daily_temp[DAYS_IN_YEAR];
/* si assegnano i valori a daily_temp[] */
for (j=0; jLa modalità di memorizzazione
degli array
Esempio
4 byte
int ar[5]; /* dichiarazione */
ar[0] = 15; 0FFC
1000 15 ar[0]
ar[1] = 17;
1004 ar[1]
ar[3] = 3; 17
1008 non definito ar[2]
ar[3]
100C 3
ar[4]
1010 non definito
1014
1018
ar[2] e ar[4] sono indefiniti: il contenuto delle posizioni di
memoria è quello rimasto da esecuzioni precedenti (garbage)
Fondamenti di Informatica I - a.a. 2020-21 6L’inizializzazione di array - 1
La presenza di valori indefiniti in alcuni elementi dell’array può
provocare errori difficili da rilevare
Þ Occorre inizializzare l’intero vettore !!
Dichiarare l’array static (vettore a durata fissa): gli elementi del
vettore, non inizializzati esplicitamente, vengono posti a zero
Valori diversi possono essere specificati, facendoli seguire alla
dichiarazione dell’array, racchiusi fra parentesi graffe: tali valori
devono essere espressioni costanti che possano essere
convertite automaticamente nel tipo dell’array
Fondamenti di Informatica I - a.a. 2020-21 7L’inizializzazione di array - 2
4 byte
Esempio
0FFC
static int ar[5];
1000 0
15 ar[0]
static int br[5] = {1,2,3.5,4,5}; 1004 ar[1]
17
0
1008 0
non definito ar[2]
100C ar[3]
0 ar[4]
1010 0
1014 1 br[0]
Nota: il valore floating-point br[1]
1018 2
3.5 è convertito nel valore 101C 3 br[2]
intero 3 1020 4 br[3]
1024 br[4]
5
1028
Fondamenti di Informatica I - a.a. 2020-21 8L’inizializzazione di array - 3
Specificare un numero maggiore di valori di inizializzazione,
rispetto agli elementi dell’array, costituisce un errore segnalato
dal compilatore
Se vengono specificati meno valori rispetto alla dimensione, gli
elementi rimanenti vengono inizializzati a zero
Esempio: La dichiarazione
static int cr[5] = {1,2,3};
produce l’inizializzazione
cr[0] = 1
cr[1] = 2
cr[2] = 3
cr[3] = 0
cr[4] = 0
Fondamenti di Informatica I - a.a. 2020-21 9L’inizializzazione di array - 4
Se vengono specificati i valori iniziali, può essere omessa la
dimensione dell’array: il compilatore calcola automaticamente il
numero degli elementi sulla base del numero dei valori iniziali
specificati
Esempio:
static char dr[] = {‘a’, ‘b’, ‘c’, ‘d’};
comporta la creazione di un array di quattro elementi, di tipo
char, caratterizzati dai valori iniziali
dr[0] = ‘a’
dr[1] = ‘b’
dr[2] = ‘c’
dr[3] = ‘d’
Fondamenti di Informatica I - a.a. 2020-21 10Uscita dal limite superiore di un array
Il compilatore, di solito, non controlla che l’accesso agli elementi
di un array venga effettuato rispettandone i limiti dimensionali
⇨ È possibile accedere per errore ad elementi per i quali non è
stata allocata memoria (aree di memoria riservate ad altre
variabili, riservate ad altri processi, etc.)
Esempio:
Essendo ar un array di 10 elementi,
main() quelli cui è possibile accedere in modo
{
int ar[10], j; corretto hanno indice da 0 a 9: il ciclo
for contiene un errore off-by-one
for (j= 0; jCrittografia - 1
Poiché in formato elettronico viene memorizzato e trasmesso ogni
tipo di informazione (anche personale, quindi coperta dalla
privacy), viene posta attenzione alla sicurezza rispetto ad accessi
indesiderati
I file, nei sistemi multiutente, sono provvisti di vari livelli di
protezione, il primo dei quali è costituito dall’autenticazione al
sistema tramite password
Oltre ai tipi di protezione standard, il contenuto di un file riservato
può essere codificato, utilizzando tecniche crittografiche che
producono, a partire dal testo in chiaro, il cosiddetto
crittogramma, o testo cifrato
Il legittimo proprietario del file (e chi da lui autorizzato) è l’unico
depositario della chiave di decodifica ed è quindi l’unico in grado
di operare l’inversione da testo cifrato a testo in chiaro
Fondamenti di Informatica I - a.a. 2020-21 12Crittografia - 2
Inoltre, negli attuali sistemi informativi distribuiti, e più in
generale nel settore delle telecomunicazioni, la crittografia ha
assunto rilievo ed interesse crescenti nelle infrastrutture di
sicurezza
Fondamenti di Informatica I - a.a. 2020-21 13Crittografia - 3
Se il sistema di cifra, o cifrario, è ben congegnato,
l’operazione di decifrazione o decifratura deve risultare
semplice al legittimo proprietario (o al destinatario del
messaggio), ma di complessità proibitiva alla “spia”
⇨ possibile in quanto gli utenti “legittimi” possiedono
un’informazione che deve rimanere inaccessibile alla spia, la
chiave del cifrario
Occorre notare la distinzione tra decifrazione e decrittazione,
l’operazione illegittima in cui non ci si può avvalere della
chiave
Fondamenti di Informatica I - a.a. 2020-21 14Crittografia - 4
/* Dato un carattere, ne fornisce un valore codificato */
#define ILLEGAL_VAL -1
Ciao
48=‘0’ ⇨ 114=‘r’
char encode(ch)
char ch;
{ 9G_5
static unsigned char encoder[128] = {127, 124, 121, 118, 115, 112,
109, 106, 103, 100, 97, 94, 91, 88, 85, 82, 79, 76, 73, 70, 67, 64, 61,
58, 55, 52, 49, 46, 43, 40, 37, 34, 31, 28, 25, 22, 19, 16, 13, 10, 7, 4,
1, 126, 123, 120, 117, 114, 111, 108, 105, 102, 99, 96, 93, 90, 87, 84,
81, 78, 75, 72, 69, 66, 63, 60, 57, 54, 51, 48, 45, 42, 39, 36, 33, 30,
27, 24, 21, 18, 15, 12, 9, 6, 3, 0, 125, 122, 119, 116, 113, 110, 107,
104, 101, 98, 95, 92, 89, 86, 83, 80, 77, 74, 71, 68, 65, 62, 59, 56, 53,
50, 47, 44, 41, 38, 35, 32, 29, 26, 23, 20, 17, 14, 11, 8, 5, 2}
/* Controlla la presenza di caratteri illeciti */
if (ch > 127)
return ILLEGAL_VAL;
else
return encoder[ch]; /* Fornisce il carattere codificato */
}
Fondamenti di Informatica I - a.a. 2020-21 15Crittografia - 5
Il codice Shift Cypher con K=3 era utilizzato da Giulio Cesare
Esercizio: Con K=11, si somma 11 al valore corrispondente alla
lettera e, nel caso che la somma superi 25, si divide il numero per 26
e si considera il resto della divisione intera
we will meet at midnight
22 4 22 8 11 11 12 4 4 19 0 19 12 8 3 13 8 6 7 19
ß
7 15 7 19 22 22 23 15 15 4 11 4 23 19 14 24 19 17 18 4
hphtwwxppelextoytrse
Fondamenti di Informatica I - a.a. 2020-21 16Gli algoritmi di ordinamento - 1
L’ordinamento di una sequenza di informazioni consiste
nel disporre le stesse informazioni in modo da rispettare
una qualche relazione d’ordine; ad esempio, una
relazione d’ordine “minore o uguale” dispone le
informazioni in modo “non decrescente”
L’ordinamento è un’operazione molto importante perché
permette di ridurre notevolmente i tempi di ricerca di
un’informazione, nell’ambito di una sequenza di
informazioni
Nel caso in cui tale sequenza risulta ordinata, secondo
una qualche relazione d’ordine, è infatti possibile
sfruttare la stessa relazione d’ordine per effettuare la
ricerca
Fondamenti di Informatica I - a.a. 2020-21 17Gli algoritmi di ordinamento - 2
Esistono due categorie di algoritmi di ordinamento: la
classificazione è fatta in base alla complessità di calcolo
e alla semplicità algoritmica
La complessità di calcolo si riferisce al numero di
operazioni necessarie all’ordinamento; tali operazioni
sono essenzialmente confronti e scambi tra gli elementi
dell’insieme da ordinare
La semplicità algoritmica si riferisce alla lunghezza e
alla comprensibilità del codice
Fondamenti di Informatica I - a.a. 2020-21 18Gli algoritmi di ordinamento - 3
Algoritmi semplici di ordinamento
Algoritmi che presentano complessità O(n2), dove n è il
numero di informazioni da ordinare: sono caratterizzati
da poche e semplici istruzioni, dunque si realizzano con
poche linee di codice
Algoritmi evoluti di ordinamento
Algoritmi che presentano complessità computazionale
O(n*log2n): sono più complessi, fanno spesso uso di
ricorsione; la convenienza del loro utilizzo si rileva
quando il numero n di informazioni da ordinare è molto
elevato
Fondamenti di Informatica I - a.a. 2020-21 19Bubblesort - 1
La strategia Bubblesort (ordinamento a bolla) prevede il
confronto dei primi due elementi di un array, e lo
scambio, se il primo è maggiore del secondo
Dopo il primo confronto, si effettua un confronto fra il
secondo ed il terzo elemento (con eventuale scambio),
fra il terzo ed il quarto, etc.
Gli elementi “pesanti” (grandi) tendono a scendere verso
il fondo del vettore, mentre quelli “leggeri” (più piccoli)
salgono (come bolle) in superficie
Fondamenti di Informatica I - a.a. 2020-21 20Bubblesort - 2
Il confronto fra tutte le coppie di elementi adiacenti viene detto
passaggio
Se, durante il primo passaggio, è stato effettuato almeno uno
scambio, occorre procedere ad un ulteriore passaggio
Ad ogni passaggio, almeno un elemento assume la sua posizione
definitiva (l’elemento più grande del sottoinsieme attualmente
disordinato)
Devono essere effettuati al più n-1 passaggi
Al k-esimo passaggio vengono effettuati n-k confronti (con
eventuali scambi): almeno k-1 elementi sono già ordinati
Complessivamente, vengono effettuati n*(n-1)/2 confronti
Þ La complessità computazionale del Bubblesort è O(n2)
Fondamenti di Informatica I - a.a. 2020-21 21Bubblesort - 3
#define FALSE 0
#define TRUE 1 Nota
#include
Nel caso migliore,
void bubble_sort(list, list_size) quando il vettore è
int list[], list_size; già ordinato, si
{ effettua un solo
int j, temp, sorted=FALSE; passaggio, con n-1
while (!sorted)
{
confronti e nessuno
sorted = TRUE; /* assume che list sia ordinato */ scambio
for (j=0; jlist[j+1]) scende a O(n)
{ /* almeno un elemento non è in ordine */
sorted = FALSE;
temp = list[j];
list[j] = list[j+1];
list[j+1] = temp;
}
} /* fine del ciclo for */
} /* fine del ciclo while */
}
Fondamenti di Informatica I - a.a. 2020-21 22Numeri casuali
Non è possibile generare veri numeri casuali con un calcolatore o
con qualsiasi metodo deterministico.
Quello che viene fatto è scrivere programmi di generazione che
producono sequenze di numeri con il maggior numero possibile di
proprietà dei numeri casuali (numeri pseudo-casuali).
Alcune proprietà sono più importanti di altre nel simulare i numeri
casuali (es. data una sequenza di numeri pseudo-casuali, ci
aspettiamo che alcuni numeri compaiano più di una volta ed altri
mai. Se tutti comparissero una volta non avremmo una serie di
numeri casuali).
Ogni numero deve avere la stessa probabilità di essere generato.
Fondamenti di Informatica I - a.a. 2020-21 23Numeri casuali - 2
Esempio di algoritmo per generare una sequenza di N numeri pseudo-
casuali compresi tra 0 e m-1:
a[1]=a1
for (i=2, iNumeri casuali - 3
In C il generatore di numeri random è l’operatore rand().
L’istruzione:
i = rand ();
genera un intero compreso tra 0 e RAND_MAX, valore definito nella libreria
(che dovrete quindi sempre includere nell’usare questo operatore).
Il valore di RAND_MAX nello standard ANSI è almeno 32767. La distribuzione
nell’intervallo è uniforme.
Fondamenti di Informatica I - a.a. 2020-21 25Numeri casuali - 4
Per ottenere una serie di altri numeri, si utilizza rand in congiunzione con
l’operatore resto. Ad esempio
rand() % 6 (6 si chiama il fattore di scala)
genera degli interi nell’intervallo tra 0 e 5.
Per traslare la serie di valori, basterà aggiungere un intero all’istruzione, che
viene detto valore di traslazione.
In generale avremo quindi che:
n = a + rand() % b
genererà numeri interi random nell’intervallo desiderato.
Fondamenti di Informatica I - a.a. 2020-21 26La direttiva #define
La direttiva #define consente di associare un nome ad una
costante
Esempio:
#define NIENTE 0
associa il nome “NIENTE” alla costante 0
Per evitare confusione fra nomi di costanti e nomi di variabili,
è pratica comune usare solo lettere maiuscole per le costanti e
solo minuscole per le variabili
L’associazione di nomi alle costanti permette…
…di semplificare la modifica del software: cambiare il valore ad
una costante equivale a cambiarne la sola definizione e non tutte
le occorrenze !!!
Fondamenti di Informatica I - a.a. 2020-21 27Puoi anche leggere