Università dell’Insubria
Facoltà di Scienze Matematiche, Fisiche e Naturali di Varese
Corso di Laurea in Informatica
Anno Accademico 2004/05
Laboratorio di Linguaggi
lezione X
Marco Tarini
Progetti a piu' files
file "auxiliary.h"
int funz1(int,int);
file "main.c"
#include "auxiliary.h"
int main(){
int x;
...
x = funz1(5, 6);
file "auxiliary.c"
#include "auxiliary.h"
int funz1(int b,int e)
{
...
}
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: schema base
file "auxiliary.h"
int funz1(int,int);
void funz2(double*);
file "main.c"
#include "auxiliary.h"
double d;
int main(){
int x;
...
x = funz1(5, 6);
...
funz2( &d );
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
file "auxiliary.c"
#include "auxiliary.h"
int funz1(int b,int e)
{
... /* corpo di funz1 */
}
void funz2(double*)
{
... /* corpo di funz1 */
}
2004/05 ‧ Università dell’Insubria
Ricordarsi di commentare!
commenti ad
alto livello!
(su cosa fanno
-in totalee come si
usano le
funzioni)
file "auxiliary.h"
/* funzione 1: blah blah */
int funz1(int,int);
/* funzione 2: blah blah */
void funz2(double*);
file "main.c"
#include "auxiliary.h"
double d;
int main(){
int x;
...
x = funz1(5, 6);
...
funz2( &d );
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
file "auxiliary.c"
#include "auxiliary.h"
int funz1(int b,int e)
{
...
/* commento implementativo */
...
}
void funz2(double*)
{ ...
}
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: schema base
main.c
preprocess.
file
precomp. compiler
1
object
file
main.o
auxiliary.h
preauxiliary.c process.
linker
eseguibile
finale
exec.exe
file
object
precomp. compiler
file
3
auxiliary.o
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: esempio di errore
file "auxiliary.h"
int funz1(int,int);
void funz2(double*);
file "main.c"
#include "auxiliary.h"
double d;
int main(){
int x;
...
x = funz1(5, 6);
...
funz2( &d );
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
file "auxiliary.c"
#include "auxiliary.h"
int funz1(int b,int e)
{
... /* corpo di funz1 */
}
void funz2(double*)
{
...niente funz 2
... /* corpo di funz1 */
}
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: esempio di errore
main.c
preprocess.
file
precomp. compiler
1
object
file
main.o
auxiliary.h
preauxiliary.c process.
linker
eseguibile
finale
exec.exe
file
object
precomp. compiler
file
3
auxiliary.o
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria
Funzioni "interne"
la funzione "funz_pippo"
non e' dichiarata nell'header.
Sarà visibile al compilatore
solo nel file in cui viene
definita.
file "main.c"
#include "auxiliary.h"
double d;
int main(){
int x;
...
x = funz1(5, 6);
...
funz2( &d );
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
file "auxiliary.h"
int funz1(int,int);
void funz2(double*);
file "auxiliary.c"
#include "auxiliary.h"
void
void funz_pippo(int
funz_pippo(int x)
x)
{
{ ...
...
}
}
int funz1(int b,int e)
{ ...
funz_pippo( b + 1);
...
}
void funz2(double*)
{ ...
}
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: collisioni
file "auxiliary.h"
int funz1(int,int);
void funz2(double*);
file "main.c"
#include "auxiliary.h"
file "auxiliary.c"
#include "auxiliary.h"
int funz_pippo()
{ ...
}
void
void funz_pippo(int
funz_pippo(int x)
x)
{
{ ...
...
}
}
double d;
int main(){
int x;
...
x = funz1(5, 6);
...
funz2( &d );
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
int funz1(int b,int e)
{ ...
funz_pippo( b + 1);
...
}
void funz2(double*)
{ ...
}
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: collisioni
main.c
preprocess.
file
precomp. compiler
1
object
file
main.o
auxiliary.h
preauxiliary.c process.
linker
eseguibile
finale
exec.exe
file
object
precomp. compiler
file
3
auxiliary.o
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: funzioni "interne"
file "auxiliary.h"
int funz1(int,int);
void funz2(double*);
file "main.c"
#include "auxiliary.h"
file "auxiliary.c"
#include "auxiliary.h"
int funz_pippo()
{ ...
}
void
void funz_pippo(int
funz_pippo(int x)
x)
{
{ ...
...
}
}
double d;
int main(){
int x;
...
x = funz1(5, 6);
...
funz2( &d );
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
int funz1(int b,int e)
{ ...
funz_pippo( b + 1);
...
}
void funz2(double*)
{ ...
}
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: funzioni "interne"
la funzione "funz_pippo"
ora non è visibile (all'esterno)
nemmeno dal linker !
file "auxiliary.h"
int funz1(int,int);
void funz2(double*);
morale della favola:
le funzioni "interne" meglio
dichiararle static
file "auxiliary.c"
#include "auxiliary.h"
file "main.c"
#include "auxiliary.h"
...
double d;
int main(){
int x;
...
x = funz1(5, 6);
...
funz2( &d );
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
void
funz_pippo(int
x)
static
void funz_pippo(int
x)
{
{ ...
...
}
}
int funz1(int b,int e)
{ ...
funz_pippo( b + 1);
...
}
void funz2(double*)
{ ...
}
2004/05 ‧ Università dell’Insubria
Progetti a piu' files
• Condivisione di...
– funzioni
– variabili
– costanti
– macros
– tipi di dato
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: condivisione variabili
file "auxiliary.h"
collisione!
multiple definition of
variable "pippo"
/* funzione 1: blah blah */
int funz1(int,int);
int pippo = 2;
file "auxiliary.c"
file "main.c"
#include "auxiliary.h"
#include "auxiliary.h"
int main(){
int x;
x = funz1(5, 6);
...
if (pippo) ...;
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
int funz1(int b,int e)
{
pippo = 16;
...
}
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: condivisione variabili
file "auxiliary.h"
/* funzione 1: blah blah */
int funz1(int,int);
extern int pippo;
file "auxiliary.c"
file "main.c"
#include "auxiliary.h"
#include "auxiliary.h"
int pippo=2;
int main(){
int x;
x = funz1(5, 6);
...
if (pippo) ...;
...
}
int funz1(int b,int e)
{
pippo = 16;
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: condivisione variabili
int pippo = 3;
definizione di una var:
1. alloca dello spazio di memoria per un nuovo intero
2. (opzionale) inizializza: scrivi "3" in quello spazio
3. d'ora in poi, pippo si riferira' a quello spazio
extern int pippo;
dichiarazione di una var:
1. "prometto che da qualche parte sara' definita una
variabile che si chiama pippo, e sara' un intero"
2. pippo si riferira' allo spazio di quella variabile
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: condivisione variabili
file "auxiliary.h"
/* funzione 1: blah blah */
int funz1(int,int);
al solito,
i commenti di
spiegazione...
/* pippo: blah blah */
extern int pippo;
file "auxiliary.c"
file "main.c"
#include "auxiliary.h"
#include "auxiliary.h"
int pippo=2;
int main(){
int x;
x = funz1(5, 6);
...
if (pippo) ...;
...
}
int funz1(int b,int e)
{
pippo = 16;
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: variabili "interne"
la variabile "i"
non e' dichiarata nell'header.
Sarà visibile (al compilatore)
solo nel file in cui viene
definita.
file "auxiliary.h"
/* funzione 1: blah blah */
int funz1(int,int);
/* pippo: blah blah */
extern int pippo;
file "auxiliary.c"
file "main.c"
#include "auxiliary.h"
int main(){
int x;
x = funz1(5, 6);
...
if (pippo) ...;
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
#include "auxiliary.h"
int pippo=2;
int i=0;
int funz1(int b,int e)
{
pippo = 16;
...
}
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: variabili "interne"
file "auxiliary.h"
collisione!
multiple definition of
variable "i"
/* funzione 1: blah blah */
int funz1(int,int);
/* pippo: blah blah */
extern int pippo;
solito probelma...
file "auxiliary.c"
file "main.c"
#include "auxiliary.h"
int i=0;
int main(){
int x;
x = funz1(5, 6);
...
if (pippo) ...;
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
#include "auxiliary.h"
int pippo=2;
int i=0;
int funz1(int b,int e)
{
pippo = 16;
...
}
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: variabili "interne"
file "auxiliary.h"
solita soluzione:
Dichiarare static
le variabili "interne".
/* funzione 1: blah blah */
int funz1(int,int);
/* pippo: blah blah */
extern int pippo;
file "auxiliary.c"
file "main.c"
#include "auxiliary.h"
int i=0;
int main(){
int x;
x = funz1(5, 6);
...
if (pippo) ...;
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
#include "auxiliary.h"
int pippo=2;
static int i=0;
int funz1(int b,int e)
{
pippo = 16;
...
}
2004/05 ‧ Università dell’Insubria
I due significati diversi di
static
1. se riferito a var locali :
"variabili che hanno lo scope di var. locali
ma sono per tutto il resto var. globali" (vedi lez. 8)
o funzioni...
2. se riferito a var globali :
"variabili non visibili all'esterno del source corrente,
neanche dal linker (= vars che il linker deve ignorare)"
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria
Progetti a piu' files
• Condivisione di...
– funzioni
– variabili
– costanti
– macros
– tipi di dato
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: condividere costanti
file "auxiliary.h"
/* funzione 1: blah blah */
int funz1(int,int);
/* pippo: blah blah */
extern int pippo;
/* MAXN: il numero max... blah blah */
const MAXN = 100;
file "main.c"
file "auxiliary.c"
#include "auxiliary.h"
#include "auxiliary.h"
int main(){
int x;
x = funz1(5, 6);
...
if (pippo) ...;
...
}
int pippo=2;
static int i=0;
Marco Tarini ‧ Laboratorio di Linguaggi ‧
int funz1(int b,int e)
{
... pippo ...
}
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: condividere macro
file "auxiliary.h"
/* funzione 1: blah blah */
int funz1(int,int);
/* pippo: blah blah */
extern int pippo;
/* MAXN: il numero max... blah blah */
#define MAXN 100
file "main.c"
file "auxiliary.c"
#include "auxiliary.h"
#include "auxiliary.h"
int main(){
int x;
x = funz1(5, 6);
...
if (pippo) ...;
...
}
int pippo=2;
static int i=0;
Marco Tarini ‧ Laboratorio di Linguaggi ‧
int funz1(int b,int e)
{
... pippo ...
}
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: condividere macro
file "auxiliary.h"
/* MAXN: il numero max... blah blah */
#define MAXN 100
typedef enum {
...
} TipoStrano;
/* funzione 1: blah blah */
int funz1(int, int);
/* pippo: blah blah */
file "main.c"
file "auxiliary.c"
extern int pippo;
#include "auxiliary.h"
#include "auxiliary.h"
int main(){
int x;
x = funz1(5, 6);
...
if (pippo) ...;
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
int pippo=2;
static int i=0;
int funz1(int b,int e)
{
... pippo ...
}
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: condividere macro
file "TipoStrano.h"
/* MAXN: il numero max... blah blah */
#define MAXN 100
typedef enum {
...
} TipoStrano;
/* funzione 1: blah blah */
int funz1(TipoStrano,int);
/* pippo: blah blah */
file "main.c"
file " TipoStrano.c"
extern int pippo;
#include "auxiliary.h"
#include "auxiliary.h"
int main(){
int x;
x = funz1(5, 6);
...
if (pippo) ...;
...
}
Marco Tarini ‧ Laboratorio di Linguaggi ‧
int pippo=2;
static int i=0;
int funz1(int b,int e)
{
... pippo ...
}
2004/05 ‧ Università dell’Insubria
Progetti a piu' files
• Condivisione di...
– funzioni
– variabili
– costanti
– macros
– tipi di dato
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria
Progetti a piu' files: perchè?
• Scopi:
– Modularità del progetto software
• dividere il progetto in aree concettualmente
separate
• mantenibilita', chiarezza...
– Separazione interfaccia / implementazione
– Riutilizzabilità del codice
– Parallelizzazione dello sviluppo software
– Riduzione tempo di ri-compilazione
• (sempre meno)
• (ma, storicamente, tra le motivazioni principali)
Marco Tarini ‧ Laboratorio di Linguaggi ‧
2004/05 ‧ Università dell’Insubria