summaryrefslogtreecommitdiffstats
path: root/doc/quick_cplusplus.md
diff options
context:
space:
mode:
authorNao Pross <naopross@thearcway.org>2019-01-25 21:59:00 +0100
committerNao Pross <naopross@thearcway.org>2019-01-25 21:59:00 +0100
commitbf4b3cb311df5e4dc685f15f338cd27c14f82a1d (patch)
tree4fb0aed30d72959b1a7c72868087d177ae93fbc0 /doc/quick_cplusplus.md
parentAdd a doc folder with a little course-like thing (diff)
downloadcplusplus-master.tar.gz
cplusplus-master.zip
Write a bunch of stuff about classes, add .gitignoreHEADmaster
Diffstat (limited to '')
-rw-r--r--doc/quick_cplusplus.md96
1 files changed, 94 insertions, 2 deletions
diff --git a/doc/quick_cplusplus.md b/doc/quick_cplusplus.md
index 411e0a3..105b4e0 100644
--- a/doc/quick_cplusplus.md
+++ b/doc/quick_cplusplus.md
@@ -131,8 +131,12 @@ chiamata anche STL) che giustamente è chiamato `std`. `std` contiene molte cose
molto utili come per esempio la `std::string`.
## Allocazione di memoria dinamica
-Come sapete è spesso utile se non necessario allocare della memoria "dinamica",
-ossia non controllata a tempo di compilazione.
+Come sapete è spesso utile se non necessario allocare della memoria "dinamica".
+A differenza del C nel C++ non ha una suddivisione cristallina tra le regioni
+di memoria quindi non si parla di stack, heap e bss (in realtà ci sono ma è
+meglio non pensarci troppo) ma semplicemente di memoria "statica" e
+"diniamica".
+
In C esistono le funzioni `malloc()` e `free()` per richiedere e liberare della
memoria. In C++ la funzione è stata integrata con delle *keywords* quali `new`
e `delete`, che si usano come segue.
@@ -145,6 +149,9 @@ int *data = new int[10];
// data = NULL;
delete data;
```
+Questo permette di fare tutte le cose sporche con i puntatori come in C, ma
+più avanti sarà mostrato come abbandonare questa fabbrica di codice che causa
+`segmentation fault`, utilizzando una cosa chiamata RAII.
## References
I puntatori del C sono molto utili, non possiamo negarlo, ma come tutti sanno
@@ -243,3 +250,88 @@ Giustamente non compila, perché il compiler non sa quale delle due funzioni si
vuole utilizzare. Ci propone però le varianti che ha trovato "`note:
candidate`" che potrebbero essere valide.
+
+
+# Classe: lo struct glorificato
+Se ancora non lo sapevate, il C++ appartiene ad una categoria di linguaggi di
+programmazione detta di paradigma *orientato ad oggetti* (Object Oriented
+Programming, OOP).
+
+Ciò non significa che siete obbligati ad abbandonare l'amato codice lineare,
+ma non potete nemmeno pretendere che l'OOP non esista.
+
+## Perché esiste `class`
+Il concetto di classe arriva da un'altra idea chiamata *incapsulazione*.
+Vediamo un esempio che ne dimostra l'utilità (importante: non si deve usare
+**sempre** l'incapsulazione, si deve usare solo quando **serve**).
+
+Okay, quindi prendiamo questo `struct`
+```C++
+struct mytime {
+ unsigned hour; // from 0 to 23
+ unsigned min; // from 0 to 59
+ unsigned sec; // from 0 to 59
+};
+```
+Molto semplice. Il problema di questo è che si può fare questo:
+```C++
+mytime when_you_will_be_productive = { 23, 61, 99 };
+when_you_will_be_productive.hour = 1234;
+```
+Ma come sapete, se non usate un qualche orologio esotico, le 22:61:99 non
+esistono. Quindi servirebbe una cosa del genere:
+```C++
+mytime make_mytime(unsigned hour, unsigned min, unsigned sec) {
+ if ((hour > 23) || (min > 59) || (sec > 59))
+ // I'll explain this later, bear with me
+ throw std::runtime_error("invalid time");
+
+ return mytime { hour, min, sec };
+}
+```
+Ma la gente, stupida com'è può comunque decidere creare degli `struct mytime`
+invalidi a mano. Quindi in C++ si fa il seguente:
+```C++
+class mytime {
+private:
+ unsigned m_hour;
+ unsigned m_min;
+ unsigned m_sec;
+
+public:
+ // this is called 'constructor'
+ mytime(unsigned hour, unsigned min, unsigned sec);
+
+ // these are 'member functions'
+ void set(unsigned hour, unsigned min, unsigned sec);
+
+ unsigned hour();
+ unsigned min();
+ unsigned sec();
+}
+```
+I membri dello `struct`, ora detto classe, sono stati resi "privati".
+E abbiamo messo delle funzioni come membri, che si chiamano quindi *funzioni
+membro*.
+
+Le funzioni membro hanno diritto di modificare i membri privati
+(come `m_hour`), mentre il mondo esterno no. Come si presentano?
+```C++
+// the variable is created by calling the constructor
+mytime example(14, 23, 55);
+
+// we can call a member function
+unsigned hour = example.hour();
+
+// but we CANNOT read or assign a private member
+example.m_min = 23; // compile error
+
+// except through a member function
+example.set(16, 23, 34);
+```
+
+Ora, non mostro l'implementazione (nel file `.cpp`) di queste funzioni, siccome
+si mostra la dichiarazione nel file header. Ma si può intuire che
+`mytime::set(...)` è simile l'esempio precedente di `make_mytime(...)`, ossia
+imposta i valori controllando che sono validi. Mentre le altre ritornano
+semplicemente una copia del valore chiesto.