Immetti la prima data (giorno, mese anno): 13 1 1973 Immetti la seconda data (giorno, mese anno): 18 11 1971 La data che viene prima nel tempo è: 18/11/1971
1 1 1 2 4 8 3 9 27 4 16 64 5 25 125 6 36 216 7 49 343 8 64 512 9 81 729 10 100 1000
0.000 0.000 0.000 0.100 0.010 0.001 0.200 0.040 0.008 0.300 0.090 0.027 0.400 0.160 0.064 0.500 0.250 0.125 0.600 0.360 0.216 0.700 0.490 0.343 0.800 0.640 0.512 0.900 0.810 0.729 1.000 1.000 1.000
inserisci b: 2 inserisci e: 3 2 alla 3 vale 8e
inserisci b: 3 inserisci e: 0 3 alla 0 vale 1
A tal fine, si scriva un programma Pi.c che usa un ciclo con una variabile intera k e itera da k=0 fino a k=x dove x è un numero intero piccolo (massimo 8...) immesso dall'utente (non si potrà mai iterare fino all'infinito). Alla fine il programma deve stampare il risultato con 20 cifre dopo la virgola. Cosa succede se x è troppo grande? Confrontate il risultato che ottenete con l'approssimazione che trovate in questa pagina. Avete ottenuto le stesse cifre? A cosa imputate l'eventuale differenza?
#include <stdio.h>
int main() {
int c;
c = getchar();
while (c != EOF) {
putchar(c);
c = getchar();
}
}
Potete usarlo lanciando ./a.outma potete anche indicare un file di input da usare come standard input al posto della tastiera, tramite la redirezione dello standard input: scaricate nella vostra directory di lavoro il file donzelletta.txt e quindi digitate:
./a.out <donzelletta.txt
./a.out <donzelletta.txtsi dovrà ottenere
Nel file c'erano 1600 caratteri
./a.out <donzelletta.txtsi dovrà ottenere sul video un output che inizia con
a o e e a ie a a a a a I u a a e o e o uo a io e e a e e a i a o U a o i i o e e i io e O e i o e uo e O a e e a i a e a i a i a i e a i e o e i i e ie e o e i i e u a a a a i a a e ie e a I o o o e i e e i io o
./a.out <donzelletta.txtsi dovrà ottenere sul video un output che inizia con
Mb epoafmmfuub wjfo ebmmb dbnqbhob, Jo tvm dbmbs efm tpmf, Dpm tvp gbtdjp efmm'fscb; f sfdb jo nbop Vo nbaapmjo ej sptf f ej wjpmf, Poef, tjddpnf tvpmf, Psobsf fmmb tj bqqsftub Ejnboj, bm eì ej gftub, jm qfuup f jm dsjof. Tjfef dpo mf wjdjof Tv mb tdbmb b gjmbs mb wfddijfsfmmb, Jodpousp mà epwf tj qfsef jm hjpsop;
./a.out <donzelletta.txtsi dovrà ottenere sul video un output che inizia con
La donzelletta vien dalla campagna, 5 parole In sul calar del sole, 5 parole Col suo fascio dell'erba; e reca in mano 9 parole Un mazzolin di rose e di viole, 7 parole Onde, siccome suole, 3 parole Ornare ella si appresta 4 parole Dimani, al dì di festa, il petto e il crine. 10 parole Siede con le vicine 4 parole Su la scala a filar la vecchierella, 7 parole Incontro là dove si perde il giorno; 7 parolee termina con
In media ho visto 5.80 parole per riga
32 40 20
33 41 21 !
34 42 22 "
35 43 23 #
36 44 24 $
37 45 25 %
38 46 26 &
39 47 27 '
40 50 28 (
41 51 29 )
42 52 2a *
43 53 2b +
44 54 2c ,
45 55 2d -
46 56 2e .
47 57 2f /
48 60 30 0
49 61 31 1
50 62 32 2
51 63 33 3
52 64 34 4
....
122 172 7a z
123 173 7b {
124 174 7c |
125 175 7d }
126 176 7e ~
Si noti che il codice decimale e il codice ottale sono
presentati su tre colonne, mentre il codice esadecimale è
presentato su due colonne. Si usino i formati di printf:
32 40 20 64 100 40 @ 96 140 60 `
33 41 21 ! 65 101 41 A 97 141 61 a
34 42 22 " 66 102 42 B 98 142 62 b
35 43 23 # 67 103 43 C 99 143 63 c
36 44 24 $ 68 104 44 D 100 144 64 d
37 45 25 % 69 105 45 E 101 145 65 e
38 46 26 & 70 106 46 F 102 146 66 f
39 47 27 ' 71 107 47 G 103 147 67 g
40 50 28 ( 72 110 48 H 104 150 68 h
41 51 29 ) 73 111 49 I 105 151 69 i
42 52 2a * 74 112 4a J 106 152 6a j
43 53 2b + 75 113 4b K 107 153 6b k
44 54 2c , 76 114 4c L 108 154 6c l
45 55 2d - 77 115 4d M 109 155 6d m
46 56 2e . 78 116 4e N 110 156 6e n
47 57 2f / 79 117 4f O 111 157 6f o
48 60 30 0 80 120 50 P 112 160 70 p
49 61 31 1 81 121 51 Q 113 161 71 q
50 62 32 2 82 122 52 R 114 162 72 r
51 63 33 3 83 123 53 S 115 163 73 s
52 64 34 4 84 124 54 T 116 164 74 t
53 65 35 5 85 125 55 U 117 165 75 u
54 66 36 6 86 126 56 V 118 166 76 v
55 67 37 7 87 127 57 W 119 167 77 w
56 70 38 8 88 130 58 X 120 170 78 x
57 71 39 9 89 131 59 Y 121 171 79 y
58 72 3a : 90 132 5a Z 122 172 7a z
59 73 3b ; 91 133 5b [ 123 173 7b {
60 74 3c < 92 134 5c \ 124 174 7c |
61 75 3d = 93 135 5d ] 125 175 7d }
62 76 3e > 94 136 5e ^ 126 176 7e ~
63 77 3f ? 95 137 5f _
Suggerimento: si conti da 32 a 62 e si stampi la riga
corrispondente. Per 32, ad esempio, si stamperà:
32 40 20 64 100 40 @ 96 140 60 `L'ultima riga verrà stampata a parte, fuori dal ciclo.
Quante righe: 12 * ** *** **** ***** ****** ******* ******** ********* ********** *********** ************Suggerimento: serve un ciclo annidato per stampare gli asterischi di ciascuna riga.
Quante righe devo stampare? 55
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
La sinusoide è ottenuta calcolando la funzione seno con un
parametro double
inizialmente pari a 0 e che viene incrementato ad ogni riga
di 0.1. Per calcolare il seno, si includa nel programma le
intestazioni della libreria matematica:
#include <math.h>e si comunichi al compilatore che si intende linkare il programma con la libreria matematica:
cc Sinusoide.c -lmLa funzione seno potrà essere calcolata nel vostro programma indicandola come sin(x) dove x deve essere di tipo double.
Inserisci un numero naturale: 461 Il decimale 461 in binario invertito si scrive 101100111che significa che il decimale 461 si scrive in binario come 111001101.
Inserisci un numero naturale: 461 Il decimale 461 in ottale invertito si scrive 517che significa che il decimale 461 si scrive in ottale come 715.
Inserisci un numero naturale: 461 Il decimale 461 in esadecimale invertito si scrive dc1che significa che il decimale 461 si scrive in esadecimale come 1cd.
Inserisci un numero naturale: 5
<- questa è una riga vuota
$$$$$
*
$$$$
**
$$$
***
$$
****
$
*****
<- questa è una riga vuota
Si noti che l'esempio sopra è fatto da 6 coppie di righe. Ciascuna
coppia è fatta da una riga di asterischi seguita da una riga di
dollari. Il numero degli asterischi aumenta dall'alto al basso (da 0 a 5)
mentre il numero dei dollari diminuisce dall'alto al basso (da 5 a 0).
Servono due cicli annidati.
Inserisci i e j: i: 5 j: 2 Inserisci i e j: i: -2 j: 3 Inserisci i e j: i: 3 j: 6 Inserisci i e j: i: 4 j: 10 Li hai immessi entrambi pari
Cosa vuoi calcolare? 1 - minimo 2 - massimo ? 3 Cosa vuoi calcolare? 1 - minimo 2 - massimo ? 2 Quanti valori hai (almeno uno) ? 0 Quanti valori hai (almeno uno) ? -1 Quanti valori hai (almeno uno) ? 10 Inserisci il valore #1: 3 Inserisci il valore #2: 5 Inserisci il valore #3: -2 Inserisci il valore #4: 21 Inserisci il valore #5: -33 Inserisci il valore #6: -11 Inserisci il valore #7: 25 Inserisci il valore #8: 12 Inserisci il valore #9: -1 Inserisci il valore #10: 5 Il massimo è 25Suggerimento: ci sono quattro fasi in questo algoritmo. Nella prima si determina se si vuole calcolare il minimo o il massimo; nella seconda si determina quanti valori ci sono nella sequenza; nella terza si leggono i valori della sequenza; nella quarta si stampa il minimo (o il massimo). Affrontate ciascuna fase separatamente e passate a programmare la fase successiva solo quando le fasi precedenti sembrano tutte funzionare.
Quante coppie casuali <x,y> devo generare (almeno una) ? 0 Quante coppie casuali <x,y> devo generare (almeno una) ? 10 x=690 y=633 : dentro x=-649 y=-975 : fuori x=409 y=-678 : dentro x=624 y=-976 : fuori x=-460 y=-102 : dentro x=-983 y=120 : dentro x=202 y=75 : dentro x=826 y=-339 : dentro x=-709 y=620 : dentro x=204 y=-666 : dentro Ne sono cadute 8 dentro e 2 fuoriQuando sarete riusciti a scrivere questo programma, aggiungete alla sua fine una istruzione di stampa dell'espressione 4.0 * dentro / q dove dentro è la quantità di coppie che sono cadute dentro al cerchio. Provate il programma per un numero grande di estrazioni casuali (per esempio, un milione). Che numero viene stampato per l'espressione precedente? Riuscite a spiegarvi perché?
a⇒b
b⇒a
c⇒c
d⇒z
e⇒y
f⇒x
g⇒r
h⇒v
i⇒u
j⇒t
k⇒s
l⇒w
m⇒q
n⇒p
o⇒o
p⇒n
q⇒m
r⇒g
s⇒k
t⇒j
u⇒i
v⇒h
w⇒l
x⇒f
y⇒e
z⇒d
da applicare anche alle lettere maiuscole. Tutti gli altri caratteri devono essere lasciati immutati. Si provi quindi ad applicare tale programma al file di testo mystery.txt:
./a.out <mystery.txtDovreste ottenere sul video qualcosa di intelligibile.
Giorno: 13 Mese: 1 Anno: 1973 Il 13/1/1973 sono passati 13 giorni dall'inizio del 1973oppure
Giorno: 24 Mese: 11 Anno: 2009 Il 24/11/2009 sono passati 328 giorni dall'inizio del 2009o ancora
Giorno: 24 Mese: 11 Anno: 2012 Il 24/11/2012 sono passati 329 giorni dall'inizio del 2012e per finire
Giorno: 24 Mese: 11 Anno: 1900 Il 24/11/1900 sono passati 328 giorni dall'inizio del 1900
Benvenuto nel servizio bancomat della BBB (Banca Banda Bassotti) Il suo credito attuale è di ben 0 euro In cosa possiamo fregiarci di esserLe utile? 1 - deposito 2 - prelievo 3 - accredito interessi 1 Quanti euro deposita? 150 Il suo credito attuale è di ben 150 euro In cosa possiamo fregiarci di esserLe utile? 1 - deposito 2 - prelievo 3 - accredito interessi 1 Quanti euro deposita? -3 Non sia infantile Quanti euro deposita? 1500 Il suo credito attuale è di ben 1650 euro In cosa possiamo fregiarci di esserLe utile? 1 - deposito 2 - prelievo 3 - accredito interessi 2 Quanti euro preleva? -1 Non sia infantile Quanti euro preleva? 2000 Non ha abbastanza soldi. Che divertente! Quanti euro preleva? 10 Il suo credito attuale è di ben 1640 euro In cosa possiamo fregiarci di esserLe utile? 1 - deposito 2 - prelievo 3 - accredito interessi 4 Non sia infantile 1 - deposito 2 - prelievo 3 - accredito interessi 3 Il suo credito attuale è di ben 1722 euro In cosa possiamo fregiarci di esserLe utile? 1 - deposito 2 - prelievo 3 - accredito interessi 1 Quanti euro deposita? 8000 Il suo credito attuale è di ben 9722 euro In cosa possiamo fregiarci di esserLe utile? 1 - deposito 2 - prelievo 3 - accredito interessi 1 Quanti euro deposita? 500 Il suo credito attuale è di ben 10222 euro Grazie per avere usato i nostri servizi I suoi 10222 euro sono stati usati per pagarci una vacanza ai tropiciIl programma deve realizzare un ciclo al cui interno viene ripetutamente posta la domanda sul tipo di operazione richiesta (1, 2 o 3). Per accredito interessi si intende un aumento del credito dell'utente pari al 5%. Eventuali risposte non sensate provocano la ripresentazione della domanda. Si noti che il prelievo deve essere impedito sia per quantità negative che per quantità che superano la disponibilità del conto. Dal ciclo si esce quando il credito supera i 10000 euro. A quel punto il programma termina.
int medio(int a, int b, int c)la quale ritorna il valore medio fra i tre valori forniti come parametro. Il programma dovrà avere anche un main() che chiede tre numeri interi all'utente, invoca la funzione medio() e stampa il risultato sul video. Per esempio, un'esecuzione di tale programma potrebbe essere:
Primo numero: -8 Secondo numero: 12 Terzo numero: -4 Il valore medio è -4
int difetto(float x) int eccesso(float x)che ricevono come parametro un numero x in virgola mobile e restituiscono l'approssimazione di x per difetto e per eccesso, rispettivamente. Il programma dovrà contenere un main() che chiede all'utente un numero a virgola mobile e quindi stampa l'approssimazione di tale numero per difetto e per eccesso. Per esempio, un'esecuzione potrebbe essere:
Inserisci il numero in virgola mobile: 3.9999 difetto(3.999900) = 3 eccesso(3.999900) = 4Non si usino funzioni della libreria matematica standard.
int bit(int num, int pos)la quale riceve come parametri un numero non negativo num e un numero non negativo pos (non va controllato, la funzione si fida di chi la chiama) e restituisce come risultato il bit pos-esimo da destra della rappresentazione binaria di num. Per esempio, bit(3,0) restituisce 1 e bit(3,2) restituisce 0. Il programma dovrà avere anche un main() che chiede all'utente un numero n fra 0 e 65535 e un altro p fra 0 e 15 (da controllare) e quindi invoca la funzione bit() e stampa il bit p-esimo da destra di n. Per esempio, un'esecuzione potrebbe essere:
Inserisci il numero (fra 0 e 65535): 65535 Inserisci la posizione del bit da destra (fra 0 e 15): 15 Il bit 15-esimo da destra di 65535 vale 1
Inserisci il numero (fra 0 e 65535): 23893 Inserisci la posizione del bit da destra (fra 0 e 15): 11 Il bit 11-esimo da destra di 23893 vale 1 Infatti in binario, su 16 bit, 23893 si scrive 0101|1|10101010101oppure
Inserisci il numero (fra 0 e 65535): 23893 Inserisci la posizione del bit da destra (fra 0 e 15): 0 Il bit 0-esimo da destra di 23893 vale 1 Infatti in binario, su 16 bit, 23893 si scrive 010111010101010|1|o infine
Inserisci il numero (fra 0 e 65535): 23893 Inserisci la posizione del bit da destra (fra 0 e 15): 15 Il bit 15-esimo da destra di 23893 vale 0 Infatti in binario, su 16 bit, 23893 si scrive |0|101110101010101
cc Main.c Libreria.c Itera.c
1 2 4 8 16 32 64 128 256 512 1024 2048 4096 8192 16384 32768
1 1 2 6 24 120 720 5040 40320 362880 3628800 39916800 479001600 6227020800 87178291200 1307674368000Si noti che l'array dovrà essere di long e non di int e che per stampare un long in printf() si usa il formato %ld.
1 1 2 3 5 8 13 21 34 55 89 144 233 377 610 987
elemento #0: 13 elemento #1: 7 elemento #2: 9 elemento #3: 8 elemento #4: 8 elemento #5: 11 elemento #6: 5 elemento #7: 2 elemento #8: 3 elemento #9: 0 elemento #10: -3 elemento #11: -2 elemento #12: 1 elemento #13: 4 elemento #14: 5 13 0 9 8 8 11 5 0 3 0 0 -2 1 4 5in cui sono stati evidenziati gli 0 che sono stati messi al posto dei tre minimi locali.
void incrementa_dispari(int x[], int length)che incrementa di uno gli elementi dispari di x fino alla posizione length-1. Infine il programma dovrà stampare l'array così modificato. Per esempio, una sua esecuzione potrebbe essere:
elemento #0: 3 elemento #1: 4 elemento #2: 5 elemento #3: 7 elemento #4: 4 elemento #5: 34 elemento #6: 43 elemento #7: 2 elemento #8: 3 elemento #9: 4 4 4 6 8 4 34 44 2 4 4
void somme_parziali(int x[], int length)che rende gli elementi di x, fino alla posizione length-1, uguali al loro vecchio valore più la somma dei vecchi valori di tutti elementi che li precedono. Infine il programma dovrà stampare l'array così modificato. Per esempio, una sua esecuzione potrebbe essere:
elemento #0: 2 elemento #1: 4 elemento #2: 2 elemento #3: 3 elemento #4: -3 elemento #5: 6 elemento #6: 11 elemento #7: 23 elemento #8: 2 elemento #9: 3 2 6 8 11 8 14 25 48 50 53
void somme_parziali2(const int sorgente[], int destinazione[], int length)che memorizza in ogni elemento in posizione i di destinazione, con 0&le i<length-1, la somma degli elementi di sorgente tra 0 ed i. Si usi l'array inserito da tastiera come sorgente e un altro array, della stessa lunghezza 10, come destinazione. Infine il programma dovrà stampare l'array usato come destinazione. Per esempio, una sua esecuzione potrebbe essere (come nell'esercizio precedente):
elemento #0: 2 elemento #1: 4 elemento #2: 2 elemento #3: 3 elemento #4: -3 elemento #5: 6 elemento #6: 11 elemento #7: 23 elemento #8: 2 elemento #9: 3 2 6 8 11 8 14 25 48 50 53
void dimezza(char s[]); void rifletti(char s[]);La prima dimezza la stringa s (cioè la tronca alla metà della sua lunghezza originaria). La seconda duplica in fondo ad s gli stessi caratteri di s, ma in ordine inverso. Tale programma dovrà avere anche una funzione main() che legge da tastiera una stringa (si usi il formato %s di scanf()) di al più 100 caratteri, la stampa, la dimezza, la stampa, la duplica e la stampa. Per esempio, una sua esecuzione potrebbe essere:
Inserisci la stringa: perdindirellina Stringa originaria: perdindirellina Stringa dimezzata: perdind Stringa riflessa: perdinddnidrep
cc CampoMinato.c Grafica.c
Gli esercizi di oggi sono un esempio di primo compitino
Inserisci la stringa: azzeccagarbugli Stringa originaria: azzeccagarbugli è una stringa alfabetica Stringa senza doppie: azecagarbuglioppure:
Inserisci la stringa: c-3ppo Stringa originaria: c-3ppo non è una stringa alfabetica Stringa senza doppie: c-3pooppure ancora
Inserisci la stringa: mannaggggia Stringa originaria: mannaggggia è una stringa alfabetica Stringa senza doppie: managiaDichiarate const i parametri delle funzioni, quando possibile.
Di quale anno vuoi la stampa? 210 solo dopo il 1600 per favore Di quale anno vuoi la stampa? 2010 1: 1 gennaio 2010 2: 2 gennaio 2010 3: 3 gennaio 2010 4: 4 gennaio 2010 5: 5 gennaio 2010 6: 6 gennaio 2010 ..................... (tutti gli altri giorni del 2010....) ..................... 362: 28 dicembre 2010 363: 29 dicembre 2010 364: 30 dicembre 2010 365: 31 dicembre 2010Si tenga conto degli anni bisestili (divisibili per 4 ma non per 100, oppure divisibili per 400).
Suggerimento: dal momento che in C una stringa è un array monodimensionale di caratteri, si conclude che in C un array di stringhe è un array bidimensionale di caratteri. Quindi potremmo definire:
char mesi[12][20] = {
"gennaio",
"febbraio",
"marzo",
"aprile",
"maggio",
"giugno",
"luglio",
"agosto",
"settembre",
"ottobre",
"novembre",
"dicembre"
};
che è l'array dei nomi dei dodici mesi dell'anno. Per esempio,
mesi[2] è la stringa "marzo".
Gli esercizi di oggi sono un esempio di primo compitino
Per esempio, delle possibili esecuzioni del programma potrebbero essere:
Inserisci la stringa: precipitevolmente Stringa originaria: precipitevolmente consonanti: prcptvlmnt; vocali: eiieoee fusione: pericipetovelemntoppure
Inserisci la stringa: aiuola Stringa originaria: aiuola consonanti: l; vocali: aiuoa fusione: laiuoaDichiarate const i parametri delle funzioni, quando possibile.
Per esempio, un'esecuzione del programma potrebbe essere:
Ho scelto il numero 49 fattore (-1 per terminare): 7 fattore (-1 per terminare): 7 fattore (-1 per terminare): -1 Bravo! Sai fare la fattorizzazione in fattori primi!oppure
Ho scelto il numero 19 fattore (-1 per terminare): 19 fattore (-1 per terminare): -1 Bravo! Sai fare la fattorizzazione in fattori primi!oppure ancora
Ho scelto il numero 97 fattore (-1 per terminare): 2 fattore (-1 per terminare): 21 i fattori devono essere numeri primi! fattore (-1 per terminare): -3 i fattori devono essere numeri primi! fattore (-1 per terminare): 11 fattore (-1 per terminare): 5 fattore (-1 per terminare): -1 Perdindirellina! Il prodotto dei tuoi fattori fa 110, non 97
int sum(const int arr[], int length, int *min, int *max, float *media)la quale riceve un array di interi arr e restituisce la somma dei primi length elementi di arr. Inoltre scrive il minimo di tali primi elementi nell'intero puntato da min; il massimo di tali primi elementi nell'intero puntato da max e la media di tali primi elementi nel float puntato da media. Si dia per scontato che length sia strettamente positivo.
Il programma dovrà anche avere un main() che chiede all'utente di immettere dieci numeri interi, che memorizza in un array di dieci interi, quindi chiama sum() con length pari a 10 e stampa somma, minimo, massimo e media.
Per esempio, un'esecuzione del programma potrebbe essere:
elemento #1: 4 elemento #2: -2 elemento #3: 3 elemento #4: 11 elemento #5: 3 elemento #6: 13 elemento #7: -89 elemento #8: 213 elemento #9: 2 elemento #10: 3 La somma degli elementi fa: 161 Il minimo elemento è: -89 Il massimo elemento è: 213 La media è: 16.100000
#include <stdio.h>
int palindroma(const char *s);
void inverti(char *s);
void elimina_spazi(char *s);
int main() {
char s[] = "Era una notte fredda e tempestosa";
char ss[] = "sator arepo tenet opera rotas";
printf("La stringa \"%s\" ", s);
if (!palindroma(s))
printf("non ");
printf("è palindroma\n");
inverti(s);
printf("L'ho invertita ottenendo \"%s\"\n", s);
elimina_spazi(s);
printf("Ho eliminato gli spazi ottenendo \"%s\"\n\n", s);
printf("La stringa \"%s\" ", ss);
if (!palindroma(ss))
printf("non ");
printf("è palindroma\n");
inverti(ss);
printf("L'ho invertita ottenendo \"%s\"\n", ss);
elimina_spazi(ss);
printf("Ho eliminato gli spazi ottenendo \"%s\"\n", ss);
return 0;
}
in modo che:
Se tutto è corretto, l'output del programma dovrà essere:
La stringa "Era una notte fredda e tempestosa" non è palindroma L'ho invertita ottenendo "asotsepmet e adderf etton anu arE" Ho eliminato gli spazi ottenendo "asotsepmeteadderfettonanuarE" La stringa "sator arepo tenet opera rotas" è palindroma L'ho invertita ottenendo "sator arepo tenet opera rotas" Ho eliminato gli spazi ottenendo "satorarepotenetoperarotas"
#include <stdio.h>
#include <string.h>
void merge(const char *orig1, const char *orig2, char *dest);
int main() {
char *s1 = "ma che bella";
char *s2 = "giornata di sole oggi!";
// creo una stringa grande abbastanza
// da contenere la fusione di s1 ed s2
char risultato[strlen(s1) + strlen(s2) + 1];
merge(s1, s2, risultato);
printf("%s\n", risultato);
}
in modo che la funzione merge() scriva dentro dest
la fusione di orig1 ed orig2, cioè un carattere
di orig1, uno di orig2, uno di orig1,
uno di orig2 e così via, cominciando dai caratteri
a sinistra e andando verso destra. Quando orig1 oppure
orig2 finisce, si continua con i caratteri restanti dell'altra
stringa.Dentro merge(), non si usi mai la notazione [] per gli array.
Se tutto è corretto, l'esecuzione del programma deve stampare:
mgai ocrhnea tbae ldlia sole oggi!
cc ContaUsi.c -o ContaUsi ./ContaUsi felicitandoseneIl suo effetto sarà di enumerare le lettere minuscole della stringa con a lato il numero di volte per cui sono usate nella stringa:
La lettera f è usata 1 volta La lettera e è usata 3 volte La lettera l è usata 1 volta La lettera i è usata 2 volte La lettera c è usata 1 volta La lettera t è usata 1 volta La lettera a è usata 1 volta La lettera n è usata 2 volte La lettera d è usata 1 volta La lettera o è usata 1 volta La lettera s è usata 1 voltaSi abbia cura di non ripetere l'informazione quando una lettera è usata più volte (come la e nell'esempio sopra) e di rispettare il singolare/plurale per volta/volte.
Se si dimentica la stringa o si inserisce più di una stringa, si deve ottenere un messaggio che ricorda l'uso corretto del programma, del tipo:
./ContaUsi felicitandosene sul serio Uso: ./ContaUsi stringa conta quante volte sono usati i caratteri minuscoli nella stringa
./Confronta uno Uno Hai inserito due parole diverseoppure
./Confronta uno uno Hai inserito due parole ugualiQuindi lo si potenzi in modo da accettare uno switch della forma -i che indica al programma di lavorare in modalità case-insensitive, ovvero di considerare lettere maiuscole e minuscole uguali. Per esempio:
./Confronta -i uno Uno Hai inserito due parole ugualioppure
./Confronta casa -i casA Hai inserito due parole ugualio ancora
./Confronta cosa cOSA -i Hai inserito due parole ugualiSi faccia in modo che lo switch possa essere inserito in qualsiasi posizione, anche più volte e anche alla fine della linea di comando. Se il programma viene invocato in modo errato, deve stampare un messaggio che ne descrive la sintassi di utilizzo e terminare. Per esempio:
./Confronta -i uno Uno tre Uso: Confronta [-i] parola1 parola2
./Occorrenze perdindirellina di La parola di occorre 2 volte dentro la parola perdindirellinaoppure
./Occorrenze perdindirellina dire La parola dire occorre 1 volta dentro la parola perdindirellinao ancora
./Occorrenze ababa aba La parola aba occorre 2 volte dentro la parola ababa
#include <stdio.h>
int mytoupper(int c);
int mytolower(int c);
int main() {
char parola[100];
char *p;
printf("Inserisci una parola: ");
scanf("%s", parola);
for (p = parola; *p; p++)
*p = mytoupper(*p);
printf("La parola in maiuscolo diventa: %s\n", parola);
for (p = parola; *p; p++)
*p = mytolower(*p);
printf("La parola in minuscolo diventa: %s\n", parola);
return 0;
}
con il codice delle due funzioni mancanti mytolower() e
mytoupper() che devono comportarsi come le funzioni di
libreria tolower() e toupper() (ovviamente, non potete
chiamare tali funzioni all'interno di quelle che dovete scrivere!). Se tutto
è corretto, il programma dovrebbe ad esempio comportarsi come segue:
Inserisci una parola: Ciao! La parola in maiuscolo diventa: CIAO! La parola in minuscolo diventa: ciao!
#include <stdio.h>
char *mystrrchr(const char *s, int c);
char *mystrstr(const char *s1, const char *s2);
int main() {
char parola1[100];
char parola2[100];
printf("Inserisci la prima parola: ");
scanf("%s", parola1);
printf("Inserisci la seconda parola: ");
scanf("%s", parola2);
printf("La porzione di %s dall'ultima a in poi è: %s\n",
parola1, mystrrchr(parola1, 'a'));
printf("La porzione di %s che comincia con %s è: %s\n",
parola1, parola2, mystrstr(parola1, parola2));
return 0;
}
con il codice delle due funzioni mancanti mystrrchr() e
mystrstr() che devono comportarsi come le funzioni di
libreria strrchr() e strstr() (ovviamente, non potete
chiamare tali funzioni all'interno di quelle che dovete scrivere!). Se tutto
è corretto, il programma dovrebbe ad esempio comportarsi come segue:
Inserisci la prima parola: cavallo Inserisci la seconda parola: va La porzione di cavallo dall'ultima a in poi è: allo La porzione di cavallo che comincia con va è: vallooppure
Inserisci la prima parola: buongiorno Inserisci la seconda parola: ciao La porzione di buongiorno dall'ultima a in poi è: (null) La porzione di buongiorno che comincia con ciao è: (null)o ancora
Inserisci la prima parola: adadada Inserisci la seconda parola: da La porzione di adadada dall'ultima a in poi è: a La porzione di adadada che comincia con da è: dadada
Se tutto è corretto, l'esecuzione del seguente programma data_main.c (che siete invitati a studiare):
#include <stdio.h>
#include "data.h"
int main() {
struct data *d, *cursore;
struct data *oggi = construct(13, 4, 2010);
int giorno, mese, anno;
do {
printf("giorno (1-31): ");
scanf("%d", &giorno);
printf("mese (1-12): ");
scanf("%d", &mese);
printf("anno (>=0): ");
scanf("%d", &anno);
}
while (!(d = construct(giorno, mese, anno)));
printf("Hai inserito il giorno %s\n", toString(d));
if (equals(d, oggi))
printf("è oggi!\n");
else {
printf("non è oggi\n");
if (compareTo(d, oggi) < 0)
printf("viene prima di oggi\n");
else {
printf("viene dopo oggi. Ecco i giorni che ci separano dal %s:\n",
toString(d));
for (cursore = successiva(oggi);
compareTo(cursore, d) < 0;
cursore = successiva(cursore)) {
printf("%s\n", toString(cursore));
}
}
}
printf("Comunque oggi è ancora il %s!\n", toString(oggi));
return 0;
}
stamperà qualcosa del tipo:
giorno (1-31): 31 mese (1-12): 4 anno (>=0): 2010 giorno (1-31): 10 mese (1-12): 6 anno (>=0): 2010 Hai inserito il giorno 10 giugno 2010 non è oggi viene dopo oggi. Ecco i giorni che ci separano dal 10 giugno 2010: 14 aprile 2010 15 aprile 2010 16 aprile 2010 17 aprile 2010 18 aprile 2010 19 aprile 2010 20 aprile 2010 21 aprile 2010 22 aprile 2010 23 aprile 2010 24 aprile 2010 25 aprile 2010 26 aprile 2010 27 aprile 2010 28 aprile 2010 29 aprile 2010 30 aprile 2010 1 maggio 2010 2 maggio 2010 3 maggio 2010 4 maggio 2010 5 maggio 2010 6 maggio 2010 7 maggio 2010 8 maggio 2010 9 maggio 2010 10 maggio 2010 11 maggio 2010 12 maggio 2010 13 maggio 2010 14 maggio 2010 15 maggio 2010 16 maggio 2010 17 maggio 2010 18 maggio 2010 19 maggio 2010 20 maggio 2010 21 maggio 2010 22 maggio 2010 23 maggio 2010 24 maggio 2010 25 maggio 2010 26 maggio 2010 27 maggio 2010 28 maggio 2010 29 maggio 2010 30 maggio 2010 31 maggio 2010 1 giugno 2010 2 giugno 2010 3 giugno 2010 4 giugno 2010 5 giugno 2010 6 giugno 2010 7 giugno 2010 8 giugno 2010 9 giugno 2010 Comunque oggi è ancora il 13 aprile 2010!Se avete completato tutto, modificate data.h in modo da gestire correttamente gli anni bisestili in construct() e in successiva().
Partito degli alberi | +++++++++++++++++++ |
che inizia col nome della barra (Partito degli alberi nell'esempio)
continua con degli spazi e poi con una barra lunga lunghezza
caratteri di cui una porzione iniziale contiene il carattere c
ripetuto (nell'esempio, c è il carattere +).
La quantità di c indica la proporzione
fra il valore della barra e totaleValori (nell'esempio,
il valore della barra deve essere circa il 45% di totaleValori)
Se tutto va bene, l'esecuzione di main.c dovrebbe stampare qualcosa del tipo:
Partito dei fiori | * |
Partito delle colline | # |
Partito dei nonni | @ |
Partito degli alberi | +++++++++++++++++++ |
Partito dei peripatetici | OO |
Partito dei dotti | *** |
Partito dei piccoli | ####### |
Partito dei lettori | @ |
Partito dei marinai | |
struct persona {
char nome[50];
int eta;
struct persona *padre;
struct persona *madre;
};
#include <stdio.h>
int seq(int n);
int main() {
int i;
for (i = 0; i < 13; i++)
printf("%d ", seq(i));
printf("\n");
return 0;
}
in modo che la funzione seq() sia ricorsiva e si comporti come segue:
3 3 5 15 19 95 101 707 715 6435 6445 70895 70907
#include <stdio.h>
void up(int x);
void down(int x);
int main(int argc, char *argv[]) {
int n = atoi(argv[1]);
printf("Conto da 0 a %d:\n", n);
up(n);
printf("\nE adesso da %d a 0:\n", n);
down(n);
return 0;
}
In modo che la funzione up(n) sia ricorsiva e stampi i numeri da
0 ad n e la funzione down(n) sia ricorsiva e stampi i numeri da
n a 0.Se tutto è corretto, l'esecuzione di up_and_down 11 deve stampare:
Conto da 0 a 11:
0
1
2
3
4
5
6
7
8
9
10
11
E adesso da 11 a 0:
11
10
9
8
7
6
5
4
3
2
1
0
#include <stdio.h>
void cambia(int centesimi);
int main(int argc, char *argv[]) {
int n = atoi(argv[1]);
cambia(n);
return 0;
}
in modo che la funzione cambia(n) sia ricorsiva e
stampi le monete necessarie per scambiare
n centesimi di euro, evitando di usarne più del dovuto (per esempio,
non si devono scambiare 200 centesimi con due monete da 1 euro, ma con una sola
moneta da 2 euro).Se tutto è corretto, l'esecuzione di cambiamonete 513 deve stampare:
una moneta da 2 euro
una moneta da 2 euro
una moneta da 1 euro
una moneta da 10 centesimi
una moneta da 2 centesimi
una moneta da 1 centesimo
#include <stdio.h>
int contiene(const char *w, char c);
int main() {
char s[100];
printf("Immetti la stringa: ");
scanf("%s", s);
if (contiene(s, 'z'))
printf("La stringa immessa contiene almeno una zeta\n");
else
printf("La stringa immessa non contiene nessuna zeta\n");
return 0;
}
in modo che la funzione contiene(w, c) restituisca true se e
solo se la stringa w contiene almeno una volta il carattere
c. Tale funzione deve essere ricorsiva.Una possibile esecuzione del programma potrebbe essere:
Immetti la stringa: ciao
La stringa immessa non contiene nessuna zeta
oppure
Immetti la stringa: andazzo
La stringa immessa contiene almeno una zeta
#include <stdio.h>
void elimina_cifre(char *w);
int main() {
char s[100];
printf("Immetti la stringa: ");
scanf("%s", s);
elimina_cifre(s);
printf("La stringa è diventata %s\n", s);
return 0;
}
in modo che la funzione elimina_cifre(w) modifichi
la stringa w trasformando le cifre numeriche che essa contiene
(cioè
i caratteri 0, 1, ..., 9) in spazi.
Tale funzione deve essere ricorsiva.Una possibile esecuzione del programma potrebbe essere:
Immetti la stringa: ciao100volte98hello1
La stringa è diventata ciao volte hello
#include <stdio.h>
int to_int(const char *w);
int main(int argc, char *argv[]) {
char *s = argv[1];
int i = to_int(s);
if (i != -1)
printf("Il binario %s (rovesciato) rappresenta il numero decimale %d\n", s, i);
else
printf("La stringa %s non rappresenta alcun numero binario\n", s);
return 0;
}
in modo che la funzione to_int(s) restituisca -1 se la
stringa s contiene caratteri diversi da 0 ed 1
e ritorni altrimenti il valore decimale di s interpretata
come numero binario rovesciato (cioè con
la cifra più significativa a destra).Per esempio, una possibile esecuzione del programma potrebbe essere
./a.out 1011
Il binario 1011 (rovesciato) rappresenta il numero decimale 13
(poiché 1101 in binario corrisponde al decimale 13) oppure
./a.out 010011g0
La stringa 010011g0 non rappresenta alcun numero binario
Tale funzione deve essere ricorsiva.
#include <stdlib.h>
#include <stdio.h>
#include "list.h"
int main() {
struct list *l1, *l2, *l3, *temp;
char *s;
int n;
l1 = construct_list
(5, construct_list
(8, construct_list
(5, construct_list
(11, construct_list
(13, NULL)))));
printf("Inserisci una lista di numeri positivi (<=0 per terminare)\n");
l2 = temp = NULL;
do {
printf("? ");
scanf("%d", &n);
if (n > 0)
if (temp)
temp = temp->tail = construct_list(n, NULL);
else
temp = l2 = construct_list(n, NULL);
}
while (n > 0);
printf("Hai immesso: %s\n", s = toString_list(l2));
free(s);
printf("Clono la lista che hai immesso\n");
l3 = clone(l2);
printf("Applico sum_elements: ");
sum_elements(l3);
printf("%s\n", s = toString_list(l3));
free(s);
printf("Clono la lista che hai immesso\n");
l3 = clone(l2);
printf("Applico sum_elements2: ");
sum_elements2(l3);
printf("%s\n", s = toString_list(l3));
free(s);
printf("La lista che hai immesso %sè un prefisso di %s\n",
prefix(l2, l1) ? "" : "non ",
toString_list(l1));
printf("E infine, la lista dei primi 12 numeri di Fibonacci: %s\n",
s = toString_list(list_fibonacci(12)));
free(s);
return 0;
}
Estendete l'implementazione delle liste vista ieri a lezione in modo
da implementare le seguenti quattro nuove funzioni, tutte ricorsive:
La soluzione è qui: list.c e list.h.
Se tutto è corretto, una possibile esecuzione del programma sarà:
Inserisci una lista di numeri positivi (<=0 per terminare) ? 5 ? 8 ? 6 ? 0 Hai immesso: [5,8,6] Clono la lista che hai immesso Applico sum_elements: [19,14,6] Clono la lista che hai immesso Applico sum_elements2: [5,13,19] La lista che hai immesso non è un prefisso di [5,8,5,11,13] E infine, la lista dei primi 12 numeri di Fibonacci: [1,1,2,3,5,8,13,21,34,55,89,144]un'altra:
Inserisci una lista di numeri positivi (<=0 per terminare) ? 5 ? 8 ? 5 ? 11 ? 13 ? 0 Hai immesso: [5,8,5,11,13] Clono la lista che hai immesso Applico sum_elements: [42,37,29,24,13] Clono la lista che hai immesso Applico sum_elements2: [5,13,18,29,42] La lista che hai immesso è un prefisso di [5,8,5,11,13] E infine, la lista dei primi 12 numeri di Fibonacci: [1,1,2,3,5,8,13,21,34,55,89,144]e un'altra ancora:
Inserisci una lista di numeri positivi (<=0 per terminare) ? 5 ? 8 ? 5 ? 11 ? 13 ? 4 ? 0 Hai immesso: [5,8,5,11,13,4] Clono la lista che hai immesso Applico sum_elements: [46,41,33,28,17,4] Clono la lista che hai immesso Applico sum_elements2: [5,13,18,29,42,46] La lista che hai immesso non è un prefisso di [5,8,5,11,13] E infine, la lista dei primi 12 numeri di Fibonacci: [1,1,2,3,5,8,13,21,34,55,89,144]
Gli esercizi di oggi sono un esempio di secondo compitino
#include <stdio.h>
#include <stdlib.h>
#include "cellulare.h"
int main() {
struct cellulare *handy = construct
("", "abc", "def", "ghi", "jkl", "mno", "pqrs", "tuv", "wxyz");
struct cellulare *lousy = construct
("himn", "xao", "bers", "pfg", "qjkl", "cd", "yz", "tuv", "w");
char parola[100];
char *s;
printf("handy:\n%s\n\n", s = toString(handy));
free(s);
printf("lousy:\n%s\n\n", s = toString(lousy));
free(s);
printf("Inserisci una parola: ");
scanf("%s", parola);
printf("Su handy devi premere i tasti %s\n", s = t9(handy, parola));
free(s);
printf("Su lousy devi premere i tasti %s\n", s = t9(lousy, parola));
free(s);
return 0;
}
Si scrivano i file
cellulare.c e
cellulare.h
che rendono disponibile
la struttura cellulare con le seguenti funzioni:
1- 2-abc 3-def
4-ghi 5-jkl 6-mno
7-pqrs 8-tuv 9-wxyz
I caratteri che seguono il - sono quelli forniti alla construct per
il corrispondente tasto
Se tutto è corretto, un'esecuzione di main.c dovrà sarà:
handy:
1- 2-abc 3-def
4-ghi 5-jkl 6-mno
7-pqrs 8-tuv 9-wxyz
lousy:
1-himn 2-xao 3-bers
4-pfg 5-qjkl 6-cd
7-yz 8-tuv 9-w
Inserisci una parola: ciao
Su handy devi premere i tasti 2426
Su lousy devi premere i tasti 6122
e un'altra sarà:
handy:
1- 2-abc 3-def
4-ghi 5-jkl 6-mno
7-pqrs 8-tuv 9-wxyz
lousy:
1-himn 2-xao 3-bers
4-pfg 5-qjkl 6-cd
7-yz 8-tuv 9-w
Inserisci una parola: camillo
Su handy devi premere i tasti 2264556
Su lousy devi premere i tasti 6211552
#include <stdlib.h>
#include <stdio.h>
#include "list.h"
int main() {
struct list *l1, *l2;
char *s;
l1 = construct
(22, construct
(5, construct
(31, construct
(11, construct
(8, NULL)))));
printf("l1 = %s\n", s = toString(l1));
free(s);
printf("Inserisci una lista di numeri positivi (<=0 per terminare)\n");
l2 = read();
printf("Hai immesso: %s\n", s = toString(l2));
free(s);
printf("Tale lista %sè una sottolista di %s\n",
sublist(l2, l1) ? "" : "non ",
s = toString(l1));
free(s);
return 0;
}
sarà del tipo:
l1 = [22,5,31,11,8]
Inserisci una lista di numeri positivi (<=0 per terminare)
? 5
? 31
? 0
Hai immesso: [5,31]
Tale lista è una sottolista di [22,5,31,11,8]
oppure:
l1 = [22,5,31,11,8]
Inserisci una lista di numeri positivi (<=0 per terminare)
? 0
Hai immesso: []
Tale lista è una sottolista di [22,5,31,11,8]
oppure:
l1 = [22,5,31,11,8]
Inserisci una lista di numeri positivi (<=0 per terminare)
? 22
? 31
? 11
? 0
Hai immesso: [22,31,11]
Tale lista non è una sottolista di [22,5,31,11,8]
Soluzione:
list.c e
list.h.