Torna indietro   Hardware Upgrade Forum > Software > Programmazione

DJI RS 5: stabilizzazione e tracking intelligente per ogni videomaker
DJI RS 5: stabilizzazione e tracking intelligente per ogni videomaker
Analizziamo nel dettaglio DJI RS 5, l'ultimo arrivato della famiglia Ronin progettato per videomaker solisti e piccoli studi. Tra tracciamento intelligente migliorato e ricarica ultra rapida, scopriamo come questo gimbal eleva la qualità delle produzioni.
AMD Ryzen 7 9850X3D: Zen 5, 3D V-Cache e frequenze al top per il gaming
AMD Ryzen 7 9850X3D: Zen 5, 3D V-Cache e frequenze al top per il gaming
AMD Ryzen 7 9850X3D è la nuova CPU gaming di riferimento grazie alla 3D V-Cache di seconda generazione e frequenze fino a 5,6 GHz. Nei test offre prestazioni superiori a 9800X3D e 7800X3D, confermando la leadership AMD nel gaming su PC.
Le soluzioni FSP per il 2026: potenza e IA al centro
Le soluzioni FSP per il 2026: potenza e IA al centro
In occasione del Tech Tour 2025 della European Hardware Association abbiamo incontrato a Taiwan FSP, azienda impegnata nella produzione di alimentatori, chassis e soluzioni di raffreddamento tanto per clienti OEM come a proprio marchio. Potenze sempre più elevate negli alimentatori per far fronte alle necessità delle elaborazioni di intelligenza artificiale.
Tutti gli articoli Tutte le news

Vai al Forum
Rispondi
 
Strumenti
Old 23-02-2009, 16:07   #1
mad_hhatter
Senior Member
 
L'Avatar di mad_hhatter
 
Iscritto dal: Oct 2006
Messaggi: 1105
[Python] duck typing e semantica

ciao a tutti, volevo intavolare una discussione su un aspetto di Python che ancora non ho ben metabolizzato: la mancanza dell'overloading dei metodi.

Dato che in Python un metodo è identificato univocamente dal suo nome (all'interno di un dato namespace), non è consentito l'overloading dello stesso.

Poco male, visto che Python si affida al duck typing. Ma sorgono comuqnue due ordini di problemi.

Il primo problema nasce quando il duck typing non può funzionare perché oggetti di tipo diverso espongono una stessa funzioalità tramite metodi aventi nomi differenti.

In tal caso ho due strade:
1. verificare il tipo del parametro
2. verificare quale metodo viene esposto dal parametro

Il primo approccio ha il difetto di obbligare il programmatore a elencare esplicitamente TUTTI i tipi che il metodo dovrà supportare.

Il secondo approccio è un'estensione del concetto di duck typing e, in quanto tale, credo sia preferibile, ma apre la strada al secondo problema a cui accennavo poco fa: cosa succede quando due oggetti diversi possiedono metodi con lo stesso nome e diverse liste di parametri?

Ad esempio, un oggetto QuerySet in Django è simile a un oggetto di tipo list, ma mentre QuerySet ha un metodo count() che restituisce il numero di elementi nel QuerySet, il metodo count di list necessita di un parametro e restituisce il numero di volte in cui tale parametro compare nella lista.

In un caso del genere, la semplice verifica della presenza del metodo count non può funzionare.


Veniamo alle domande:
1. esiste un approccio che permetta di gestire entrambe le situazioni senza dover cambiare idioma?

2. è stato introdotto in python 3.0 un metodo per gestire queste situazioni? (mi pare ne avesse accennato raymond hettinger alla PyCon2 italia, forse le annotation?)
mad_hhatter è offline   Rispondi citando il messaggio o parte di esso
Old 23-02-2009, 17:02   #2
cdimauro
Senior Member
 
L'Avatar di cdimauro
 
Iscritto dal: Jan 2002
Città: Germania
Messaggi: 26110
Quote:
Originariamente inviato da mad_hhatter Guarda i messaggi
ciao a tutti, volevo intavolare una discussione su un aspetto di Python che ancora non ho ben metabolizzato: la mancanza dell'overloading dei metodi.

Dato che in Python un metodo è identificato univocamente dal suo nome (all'interno di un dato namespace), non è consentito l'overloading dello stesso.

Poco male, visto che Python si affida al duck typing. Ma sorgono comuqnue due ordini di problemi.

Il primo problema nasce quando il duck typing non può funzionare perché oggetti di tipo diverso espongono una stessa funzioalità tramite metodi aventi nomi differenti.
Se gli oggetti hanno metodi diversi, c'è poco da fare. Al limite puoi creare un metodo di una classe con lo stesso nome di quello usato nell'altra, rimappandolo se l'interfaccia è diversa, oppure riciclando direttamente quello col nome diverso che espone la medesima funzionalità.
Quote:
In tal caso ho due strade:
1. verificare il tipo del parametro
2. verificare quale metodo viene esposto dal parametro

Il primo approccio ha il difetto di obbligare il programmatore a elencare esplicitamente TUTTI i tipi che il metodo dovrà supportare.

Il secondo approccio è un'estensione del concetto di duck typing e, in quanto tale, credo sia preferibile, ma apre la strada al secondo problema a cui accennavo poco fa: cosa succede quando due oggetti diversi possiedono metodi con lo stesso nome e diverse liste di parametri?

Ad esempio, un oggetto QuerySet in Django è simile a un oggetto di tipo list, ma mentre QuerySet ha un metodo count() che restituisce il numero di elementi nel QuerySet, il metodo count di list necessita di un parametro e restituisce il numero di volte in cui tale parametro compare nella lista.

In un caso del genere, la semplice verifica della presenza del metodo count non può funzionare.

Veniamo alle domande:
1. esiste un approccio che permetta di gestire entrambe le situazioni senza dover cambiare idioma?
Se i metodi si chiamano allo stesso modo, ma hanno parametri e/o funzionamento diversi, non si possono conciliare le due cose.

Al limite potresti estendere uno dei due oggetti in modo da sovrascrivere il metodo count di uno e farlo funzionare esattamente come l'altro. Ma in questo modo se passi l'oggetto a una funzione che si aspetta il count originale, non funzionerebbe più nulla.

La soluzione è di avere un'interfaccia comune che implementano entrambe le classi, e personalmente mi affiderei alla funzione built-in len(), che già funziona con le liste restituendo il numero di elementi che contiene.

Estenderei poi QuerySet in questo modo:
Codice:
class MyQuerySet(QuerySet):
  def __len__(self):

    return QuerySet.count(self)
Oppure:
Codice:
class MyQuerySet(QuerySet):

  __len__ = QuerySet.count
Visto che __len__ e count hanno esattamente la stessa interfaccia (non hanno nessun parametro, a parte self, e restituiscono un valore numerico che è proprio ciò che si vuole).

A questo punto utilizzerei len() per entrambi i tipi di oggetto.
Quote:
2. è stato introdotto in python 3.0 un metodo per gestire queste situazioni? (mi pare ne avesse accennato raymond hettinger alla PyCon2 italia, forse le annotation?)
Le annotation servono soltanto per annotare, appunto, informazioni sui parametri di una funzione (o metodo) e/o sul valore restituito. Ma sono a puro scopo informativo: Python non le usa per determinare il tipo di oggetto passato a una funzione, perché ciò avviene sempre e comunque in maniera dinamica, a runtime e al momento preciso in cui viene poi usato l'oggetto passato come parametro.

Tutto ciò ovviamente se ho capito cosa intendevi.

Se ti servono altre informazioni, chiedi pure.
__________________
Per iniziare a programmare c'è solo Python con questo o quest'altro (più avanzato) libro
@LinkedIn Non parlo in alcun modo a nome dell'azienda per la quale lavoro
Ho poco tempo per frequentare il forum; eventualmente, contattatemi in PVT o nel mio sito. Fanboys
cdimauro è offline   Rispondi citando il messaggio o parte di esso
Old 23-02-2009, 17:42   #3
mad_hhatter
Senior Member
 
L'Avatar di mad_hhatter
 
Iscritto dal: Oct 2006
Messaggi: 1105
ciao cesare, grazie per le risposte.

Avevo già preso in considerazione le tue soluzioni, il problema è che a volte sono decisamente overkill rispetto al problema da risolvere. Inoltre nel cas di django il problema è che QuerySet non si crea esplicitamente ma viene restituito attraverso dei factory method quindi oltre a estendere QuerySet dovrei modificare il framework per restituire il nuovo tipo esteso...

Per le annotazioni, probabilmente avevo frainteso il discorso di Raymond.

Grazie per l'aiuto, prezioso come sempre
mad_hhatter è offline   Rispondi citando il messaggio o parte di esso
Old 23-02-2009, 22:13   #4
cdimauro
Senior Member
 
L'Avatar di cdimauro
 
Iscritto dal: Jan 2002
Città: Germania
Messaggi: 26110
Quote:
Originariamente inviato da mad_hhatter Guarda i messaggi
ciao cesare, grazie per le risposte.

Avevo già preso in considerazione le tue soluzioni, il problema è che a volte sono decisamente overkill rispetto al problema da risolvere. Inoltre nel cas di django il problema è che QuerySet non si crea esplicitamente ma viene restituito attraverso dei factory method quindi oltre a estendere QuerySet dovrei modificare il framework per restituire il nuovo tipo esteso...
Ah, ho capito. In questo caso le soluzioni che ti propongo sono due, e non necessitano di estendere nessuna classe, perché sfruttano appunto la dinamicità intrinseca di Python.

Soluzione 1. Supposto che la classe QuerySet si trovi nel modulo x.y.z:
Codice:
x.y.z.QuerySet.__len__ = x.y.z.QuerySet.count
da piazzare ovviamente dopo l'import di x.y.z e prima di utilizzare QuerySet.

Soluzione2. Supponiamo che foo() sia la funzione che torni un'istanza di QuerySet:
Codice:
Records = x.y.z.foo()
Records.__len__ = Records.count
Si tratta di due soluzioni simili, visto che sostanzialmente fanno la stessa cosa: aggiungere il metodo __len__.
Solo che la prima lo fa alla classe base, per cui una volta aggiunto ad essa verrà automaticamente ereditato da tutte le istanze di QuerySet, incluse quelle già create.
La seconda soluzione invece lo aggiunge soltanto all'istanza appena creata.

Una parziale riscrittura della seconda soluzione potrebbe essere questa:
Codice:
def DecoratedQS(Instance):
  Instance.__len__ = Instance.count
  return Instance

Records = DecoratedQS(x.y.z.foo())
O, meglio ancora, creando una funzione foo "locale" che esegue il wrapping di quella che usi nel modulo x.y.z:
Codice:
def foo():
  Instance = x.y.z.foo()
  Instance.__len__ = Instance.count
  return Instance

Records = foo()
Personalmente mi piace di più quest'ultima, perché non "sporca" né la classe QuerySet, che mantiene la propria identità, né allunga la stesura del codice dovendo passare l'istanza creata a una funzione per poi finalmente poterla utilizzare.
Quote:
Per le annotazioni, probabilmente avevo frainteso il discorso di Raymond.
Può essere, perché sono soltanto elementi decorativi.

Per curiosità: ma hai sentito Raymond alla scorsa PyCon2, oppure da qualche altra parte?
Quote:
Grazie per l'aiuto, prezioso come sempre
Figurati. E' un piacere cercare di essere utile, nei limiti del tempo che ho a disposizione.

Come vedi soluzioni ai problemi ne esistono diverse (probabilmente ce ne saranno altre). La cosa bella che trovo in Python è che grazie alla sua dinamicità è possibile crearne di utili e interessanti che con altri linguaggi nemmeno mi sarei sognato di fare, in quanto non possibili o estremamente macchinosi. Il tutto mantenendo il codice sempre pulito ed elegante.

Per lo meno, questa è l'impressione che ho dopo un po' di anni che ci lavoro.
__________________
Per iniziare a programmare c'è solo Python con questo o quest'altro (più avanzato) libro
@LinkedIn Non parlo in alcun modo a nome dell'azienda per la quale lavoro
Ho poco tempo per frequentare il forum; eventualmente, contattatemi in PVT o nel mio sito. Fanboys
cdimauro è offline   Rispondi citando il messaggio o parte di esso
Old 23-02-2009, 23:01   #5
mad_hhatter
Senior Member
 
L'Avatar di mad_hhatter
 
Iscritto dal: Oct 2006
Messaggi: 1105
mmm... queste ultime soluzioni mi piacciono particolarmente: sono concise e molto chiare. Grazie molte!

Si, ho sentito Raymond alla PyCon2, ma all'epoca della conferenza avevo alle spalle solo una settimana di python per cui molto probabilmente ho frainteso alcuni discorsi su python 3.0

Da allora python è il linguaggio che uso ogni giorno al lavoro (devo ringraziare il mio capo e un collega per questo ) e non smetto di rendermi conto di quanto sia divertente e stimolante, soprattutto non smette di sorprendermi con soluzioni impensabili con altri linguaggi. A volte mi rendo conto che è necessario spogliarsi di alcuni costrutti acquisiti essendo cresciuto con Java all'università per poter apprezzare appieno python.
mad_hhatter è offline   Rispondi citando il messaggio o parte di esso
Old 23-02-2009, 23:07   #6
cdimauro
Senior Member
 
L'Avatar di cdimauro
 
Iscritto dal: Jan 2002
Città: Germania
Messaggi: 26110
E' esattamente lo stesso motivo che mi ha portato a "innamorarmi" di Python, che ormai uso quasi esclusivamente per lavorare. Con lui ho ritrovato il piacere di programmare in maniera "creativa".

Comunque alla PyCon2 c'ero pure io, ed ero quello che ha sparato a Raymond le ultime tre domande di fila e a cui volevano strappare via il microfono.
__________________
Per iniziare a programmare c'è solo Python con questo o quest'altro (più avanzato) libro
@LinkedIn Non parlo in alcun modo a nome dell'azienda per la quale lavoro
Ho poco tempo per frequentare il forum; eventualmente, contattatemi in PVT o nel mio sito. Fanboys
cdimauro è offline   Rispondi citando il messaggio o parte di esso
Old 24-02-2009, 10:12   #7
mad_hhatter
Senior Member
 
L'Avatar di mad_hhatter
 
Iscritto dal: Oct 2006
Messaggi: 1105
Quote:
Originariamente inviato da cdimauro Guarda i messaggi
E' esattamente lo stesso motivo che mi ha portato a "innamorarmi" di Python, che ormai uso quasi esclusivamente per lavorare. Con lui ho ritrovato il piacere di programmare in maniera "creativa".

Comunque alla PyCon2 c'ero pure io, ed ero quello che ha sparato a Raymond le ultime tre domande di fila e a cui volevano strappare via il microfono.
purtroppo non ricordo, ma magari ci vedremo a maggio a PyCon 3
mad_hhatter è offline   Rispondi citando il messaggio o parte di esso
 Rispondi


DJI RS 5: stabilizzazione e tracking intelligente per ogni videomaker DJI RS 5: stabilizzazione e tracking intelligent...
AMD Ryzen 7 9850X3D: Zen 5, 3D V-Cache e frequenze al top per il gaming AMD Ryzen 7 9850X3D: Zen 5, 3D V-Cache e frequen...
Le soluzioni FSP per il 2026: potenza e IA al centro Le soluzioni FSP per il 2026: potenza e IA al ce...
AWS annuncia European Sovereign Cloud, il cloud sovrano per convincere l'Europa AWS annuncia European Sovereign Cloud, il cloud ...
Redmi Note 15 Pro+ 5G: autonomia monstre e display luminoso, ma il prezzo è alto Redmi Note 15 Pro+ 5G: autonomia monstre e displ...
NASA Perseverance ha utilizzato percorsi...
Blue Origin sospende per almeno due anni...
Stampanti, Los Angeles verso il divieto ...
Roscosmos Amur: il razzo spaziale riutil...
Robot aspirapolvere per tutte le tasche:...
Accedere alle mail di un lavoratore lice...
Amazon Haul scatenato: migliaia di prodo...
Amazon Seconda Mano rilancia: sconto ext...
Super prezzo Amazon per ECOVACS DEEBOT T...
NVIDIA Shield TV: dieci anni di aggiorna...
Le 10 offerte migliori su Amazon oggi, c...
Autostrade che 'pensano': l'AI arriva su...
AMD alza l'asticella: Zen 6 è la ...
Il satellite spia russo Olymp-1 si &egra...
Rocket Lab prosegue l'assemblaggio del n...
Chromium
GPU-Z
OCCT
LibreOffice Portable
Opera One Portable
Opera One 106
CCleaner Portable
CCleaner Standard
Cpu-Z
Driver NVIDIA GeForce 546.65 WHQL
SmartFTP
Trillian
Google Chrome Portable
Google Chrome 120
VirtualBox
Tutti gli articoli Tutte le news Tutti i download

Strumenti

Regole
Non Puoi aprire nuove discussioni
Non Puoi rispondere ai messaggi
Non Puoi allegare file
Non Puoi modificare i tuoi messaggi

Il codice vB è On
Le Faccine sono On
Il codice [IMG] è On
Il codice HTML è Off
Vai al Forum


Tutti gli orari sono GMT +1. Ora sono le: 12:10.


Powered by vBulletin® Version 3.6.4
Copyright ©2000 - 2026, Jelsoft Enterprises Ltd.
Served by www3v