Funzioni:
Parametri in ingresso
- una cosa molto utile e' definire dei parametri di default:
def
richiesta_conferma(prompt, num=4, ris='rispondi Si o No !'):
while True:
ok = raw_input(prompt)
if ok in ('s\r', 'si\r', 'S\r', 'Si\r'): return True
if ok in ('n\r', 'no\r', 'N\r', 'No\r'): return False
num -= 1
if num < 0:
raise IOError('errore Utente')
print ris

# mettiamola in uso
res = richiesta_conferma('Vuoi realmente uscire?')
if res == True:
print 'hai richiesto di uscire'
else:
print 'hai richiesto di NON uscire'
si puo' operare sui parametri della funzione o per posizione o per nome !
i valori di default vengono valutati solo una volta quando la funzione e' creata !
i valori di default devono essere definiti per ultimi !

Parametri arbitrari in ingresso
- questo metodo e' molto usato

# *args non e' altro che una tupla
def
fprintf (file, format, *args):
        file.write(format %args)

# se si vuol passare una lista di default:che si accumula
def f(a, L=[]):
        L
.append(a)     # print f(1) risponde con [1]
        return L            # print f(2) risponde con [1, 2]
# se invece si vuol passare una lista di default:che non venga accumulata
def
f(a, L=none):
        if L is None:     # print f(1) risponde con [1]
        L
= []              # print f(2) risponde con [2]
        L
.append(a)
        return
L
# se si vuol passare un dizionario
def f(**b):
        print(b)           # la mettiamo in uso f(pippo=10)

Classi:
Fondamenti
 - un oggetto ha due parti fondamentali
    Attributi
    - contengono i dati dell'oggetto (variabili)
    Metodi
    - sono le funzioni con accesso implicito

una Classe definisce una struttura (“Attributi , Metodi”) e permette di creare degli oggetti
un oggetto della stessa classe condivide i Metodi e la stessa Lista di Attributi
    (ma non gli stessi valori, se non sono di tipo statico)

# Definizione
class
Rettangolo(object):     # (object) nuovo modo per definire una classe madre
    "Questa e' la solita DocString"
    def
__init__(self, base, altezza):         # questo e' un metodo speciale
        "questo e' il costruttore"                # viene chiamato ogni qualvolta si istanzia
        self
.base = base                           # un oggetto, serve ad inizializzare
        self
.altezza = altezza                     # i parametri
    def area(self):                                   # questo e' un metodo della classe
        "calcola area"
        return
self.base * self.altezza

Ereditarieta'
 - le Classi costituiscono una gerarchia e possono derivare da altre classi
    ereditando metodi e attrributi. (La classe madre e' detta anche superclasse)
- si puo' ereditare anche da piu' classi contemporaneamente (eredita' multipla)

# Classe base
class
Geom(object):
    "classe base di geometria"

    def desc(self):                                 #descrivo i miei attributi
        print "la mia Area e' %s" %(self.area())
# Classe derivata
class Rett(Geom):
    "Questa classe e' derivata dalla superclasse Geometria"

    def
__init__(self, base, altezza):     # questo e' un metodo speciale
        "questo e' il costruttore"            # viene chiamato ogni qualvolta si istanzia
        self.base = base                        # un oggetto, serve ad inizializzare i
        self.altezza = altezza                  # i parametri
    def area(self):                                 # questo e' un metodo della classe
        "calcola area"
        return
self.base * self.altezza
# altra Classe derivata
class Cerchio(Geom):
    "Questa classe e' derivata dalla superclasse Geometria"

    def
__init__(self, raggio):
        self.raggio = raggio
    def
area(self):
        "calcola l'area"
        import math
        return math.pi * self.raggio * self.raggio


# Mettiamo in uso le classi derivate:
>> import fGeom                        # richiamo il file dove abbiamo definito le classi
>> r = fGeom.Rett(2,3)              # istanzio l'oggetto rettangolo
>> c = fGeom.Cerchio(10)         # istanzio l'oggetto cerchio
>> r.desc()                                 # richiamo il metodo desc del rettangolo !
la mia Area e' 6
>> c.desc()                                 # richiamo il metodo desc del cerchio !
la mia Area e' 314.15


Polimorfismo
 - la possibilita' che l'esecuzione di uno stesso metodo abbia effetti diversi in
    base all'oggetto che deve trattare.
- abbiamo visto che l'oggetto rettangolo richiama il calcolo dell'area nello
    stesso modo dell'oggetto cerchio! Pero' ognuno opera in modo diverso
Override (sovrapposizione)
- una Classe derivata (sottoclasse) puo'  implementare il proprio metodo
     ed avere accesso anche al metodo originale
Metodi Virtuali
- quando si dichiara un metodo senza fornire l'implementazione
    l'implementazione e' affidata alla classe figlio.
Metodi e Variabili Private
- in python si definiscono privati tutti gli oggetti che iniziano con 2 undescore
    e finiscono senza (es: __mioParametro)
    se finiscono con 2 underscore sono considerati speciali (es: __init__)
    ma sono raggiungibili anche al di fuori della classe!

Eccezioni :
- Condizioni particolori in cui si deve decidere se interrompere l'esecuzione e informare l'utente.
- esempi:
    si tenta di leggere un file inesistente
    si cerca di dividere un numero per zero
Costrutto
try:
- si tenta di eseguire un blocco di codice
except:
- il blocco di codice che gestisce l'eccezione
raise:
- si solleva una eccezione o si riattiva quella intercettata

# Esempio
import
sys
try: f = open("mioFile.txt")                 # apro il file
    s = readline()                                # leggo una linea
    i = int(s.strip())                             # converto in intero il dato
except IOError(errno, strerror):        # gestione di una particolare
    # eccezione con parametri
   
print "Errore I/O (%s): %s" %(errno, strerror)
except ValueError:                           # gestione di una particolare
    print
"Non si puo' convertire il dato in un intero"
except:                                             # gestione generica
    print "Errore inatteso:"
    sys.exc_info()[0]
raise
                                                # passo la gestione al sistema

e-mail _orciml_@gmail.com eliminare gli underscore per ottenere l'indirizzo corretto!!!