Passa al tema normale
Discussioni su argomenti di Informatica

Regole del forum

Consulta il nostro regolamento e la guida per scrivere le formule
Rispondi al messaggio

Che cos'è una variabile? (o anche "passaggio by-? in Python")

06/01/2020, 00:53

Ciao.

1) Per il linguaggio C++ (o in C) che cos'è una variabile? (mi interessa capirlo "a basso livello"). In altre parole, mi rimbomba nella testa che "le istanze di tipi primitivi sono storate nello stack, mentre gli oggetti più complessi possono essere messi nello heap", ma che significa esattamente ciò? La riga di codice int p = 0; "dichiara e inizializza una variabile" p: posso vedere p esattamente come il numero 0? O è più giusto pensare a essa come ad un contenitore per l'indirizzo di un oggetto 0 nello stack? (Non mi pare di ricordare di "un'indirizzo di una cosa nello stack", però...).

2) Che accade in Java? Per quanto ne so, le variabili lì sono effettivamente dei contenitori per un indirizzo, di una cosa che però è automaticamente storata nel posto più consono (secondo il compilatore, non secondo il programmatore). Se però consideriamo le chiamate dei metodi
Codice:
public static void foo_1(Foo f) {
  f = new Foo();
}

Codice:
public static void foo_2(Foo f) {
  f.fuckUp();
}

su un oggetto di tipo Foo avente un metodo fuckUp abbastanza autoesplicativo, ad esempio come
Codice:
Foo f = new Foo();
foo_1(f);
// f è ancora lo stesso di prima
// ma...
foo_2(f);
// ...ora no >:S

ci accorgiamo di alcune stranezze. Il motivo di tali è la scelta progettuale di nascondere i puntatori e gli operatori * e -> di dereference; più il fatto che i riferimenti in stile C++ in Java non ci sono: il che rende "strano" il comportamento di cose passate by-value (unica "modalità di passaggio" di cui Java dispone, in ogni caso). Sbaglio? È per questo che certe persone inveiscono contro chi usa il termine "puntatore", riguardo a Java?

3) Veniamo a Python (2.7). Non mi è molto chiara la cosa. Il prof. non vuole sentir chiamare le variabili "variabili" (tantomeno "puntatori"), ma "riferimenti". Mi sembra però che Python non superi lo swap-test (non posso definire una funzione swap che (pseudocodice)
Codice:
swap(a,b) {
  tmp = a
  a = b
  b = tmp
}

a, b = 10,57
swap(a,b)
// a,b sono ora 57,10
)

Questa cosa si può fare eccome in C++:
Codice:
void swap(Foo& a, Foo& b) {
  Foo tmp = a;
  a = b;
  b = tmp;
}

appunto perché in C++ esistono i riferimenti (o alias) veri, non come in Java. E in Python, cosa sono le variabili (o chi per loro)?

(scusate per gli abusi di linguaggio: è da un sacco che non tocco queste cose).

Re: Che cos'è una variabile? (o anche "passaggio by-? in Python")

06/01/2020, 07:33

ma che significa esattamente ciò? La riga di codice int p = 0; "dichiara e inizializza una variabile" p: posso vedere p esattamente come il numero 0?
O è più giusto pensare a essa come ad un contenitore per l'indirizzo di un oggetto 0 nello stack?


Il compilatore mantiene una tabella dei simboli: quando incontra per la prima volta una dichiarazione, crea un'associazione tra l'identificatore e l'indirizzo di memoria corrispondente. Dopodichè ogni occorrenza dell'identificatore nel codice viene sostituita con il relativo indirizzo.
Quindi una variabile non è il contenitore di un indirizzo, ma ne è un'alias.
Nel caso in cui la variabile sia di tipo puntatore, però, sarà sempre un nome associato alla relativa area di memoria,
ma questa avrà all'interno a sua volta un indirizzo: puoi quindi vederla effettivamente come un contenitore.

Ora, quello che credo ti crei confusione è che il concetto di riferimento in C++ è differente rispetto a quello di Java e Python.
Nel primo è un nome alternativo associato ad una variabile e puoi pensarlo come un'altra entry nella tabella detta sopra, quindi passarlo a foo_1() sarebbe come riferirsi alla variabile originaria; nel secondo è qualcosa di molto simile ad un puntatore. Ipotizzando di voler far funzionare foo_1() in C, che al contrario di C++ non ha il tipo riferimento, sarebbe necessario un puntatore a puntatore. Facendo il parallelo con Java, ci mancherebbe un livello di indirizzamento.


ci accorgiamo di alcune stranezze.

Non ho capito perchè parli di stranezze, è il comportamento normale del passaggio per valore. Dovrebbe essere così anche in C++, se non usi i riferimenti.

È per questo che certe persone inveiscono contro chi usa il termine "puntatore", riguardo a Java?

Chi contesta il termine si riferisce probabilmente ad alcune limitazioni rispetto ai puntatori di C/C++: niente aritmetica o conversioni numeriche, e forse alcune caratteristiche oscure di cui non sono al corrente. D'altronde, l'eccezione NullPointerException su un riferimento nullo suggerisce che ci sia almeno una qualche affinità :)

Il prof. non vuole sentir chiamare le variabili "variabili" (tantomeno "puntatori"), ma "riferimenti". [...] E in Python, cosa sono le variabili (o chi per loro)?


In Java le variabili possono essere di un tipo primitivo (int, double, ...) o un riferimento ad un oggetto. In Python tutto è un oggetto, anche un intero. Quindi tutte le variabili sono riferimenti.

Re: Che cos'è una variabile? (o anche "passaggio by-? in Python")

06/01/2020, 12:50

Grazie per la risposta!

probid ha scritto:Il compilatore mantiene una tabella dei simboli
Ok. Mi è più chiaro.

probid ha scritto:Non ho capito perchè parli di stranezze, è il comportamento normale del passaggio per valore. Dovrebbe essere così anche in C++, se non usi i riferimenti.
Le ho chiamate "stranezze" perché il comportamento dei metodi foo_1 e foo_2 non è coerente con il fatto che Foo f = new Foo();, in Java, è un puntatore (o qualcosa di molto molto simile). Considera quello che succederebbe in C++: quali tra questi metodi si comportano come l'analogo in Java?
Codice:
void foo_1(Foo* f) {
  f = new Foo();
}

void foo_2a(Foo* f) {
  f.fuckUp();
}

void foo_2b(Foo* f) {
  f->fuckUp();
}


Sono foo_1 e foo_2b (mentre foo_2a, che mi auguro non abbia senso nemmeno in C++, è scritto esattamente come se stessi digitando codice Java). Se i riferimenti di Java (o di Python, in base a quanto ho capito) fossero riferimenti veri, un chiamata a foo_1 avrebbe effetti collaterali (e invece non ne ha). Se i puntatori di Java fossero veri puntatori, non dovrebbe essere nemmeno possibile chiamare foo_2a (perché, in genere, un puntatore non ha un metodo fuckUp().

Il punto è che posso dire lo stesso in Python (ho appena provato con una lista e il suo metodo pop). Mi confermi che il comportamento delle "variabili" in Python è esattamente lo stesso che in Java, ossia quello di "puntatori" senza aritmetica dove non c'è mai bisogno di dereference (dei * e -> C++-like)?

(Abbi pietà: ho ripreso in mano queste cose ieri sera, dopo tre anni che le ignoravo felicemente :-D )

Re: Che cos'è una variabile? (o anche "passaggio by-? in Python")

08/01/2020, 17:30

Sergio ha scritto:Maggiori dettagli qui.
Stavo cercando esattamente di capire meglio la discussione a quel link.

Mi incasina che né in Java né in Python ci sia un distinzione "morfologica" tra "variabili" (o chi per loro) e "puntatori" (o chi per loro), e che i riferimenti non abbiano nulla a che vedere con i riferimenti C++-like.

Credo di aver chiarito, comunque. Però devo vedermi meglio la storia sugli immutable objects in Python. (E non ha senso che inizi a parlarne ora perché dire cavolate :-D )

Re: Che cos'è una variabile? (o anche "passaggio by-? in Python")

08/01/2020, 17:30

Sergio ha scritto:Maggiori dettagli qui.
Stavo cercando esattamente di capire meglio la discussione a quel link.

Mi incasina che né in Java né in Python ci sia un distinzione "morfologica" tra "variabili" (o chi per loro) e "puntatori" (o chi per loro), e che i riferimenti non abbiano nulla a che vedere con i riferimenti C++-like.

Credo di aver chiarito, comunque. Però devo vedermi meglio la storia sugli immutable objects in Python. (E non ha senso che inizi a parlarne ora perché direi cavolate :-D )
Rispondi al messaggio


Skuola.net News è una testata giornalistica iscritta al Registro degli Operatori della Comunicazione.
Registrazione: n° 20792 del 23/12/2010.
©2000— Skuola Network s.r.l. Tutti i diritti riservati. — P.I. 10404470014.