Forum >> Principianti >> memorizzazione immagini

Pagina: 1 2 Avanti

buongiorno a tutti

volevo chiedere un chiarimento
image = PhotoImage(file="photo.gif")
print(image.cget('file'))
print(image)
questo invece è il risultato del print:

photo.gif
pyimage1


tramite "image.cget" recupero il nome del file

ho fatto molte prove senza riuscirci e mi chiedo:

è possibile ottenere il nome del file usando "pyimage1" ?

grazie.


--- Ultima modifica di pypy in data 2018-10-11 12:58:38 ---
Che cos'è "PhotoImage"? In generale per cortesia evitate di usare nomi, moduli, librerie, componenti vari senza dire che cosa sono, da che cosa li avete importati. Non è che possiamo tirare a indovinare.


E in ogni caso... da quello che scrivi sembra che "pyimage1" sia semplicemente la rappresentazione dell'oggetto che la tua libreria crea quando apri un'immagine. File immagine -> caricato in un oggetto python -> chiamo __repr__ su quell'oggetto (con print, per esempio) e ottengo "pyimage1". Quindi "pyimage1" non è niente, è solo una stringa di convenienza che python sputa fuori in risposta a una chiamata "oggetto.__repr__()" (una chiamata che per esempio avviene quando fai un print). L'oggetto non è "pyimage1", l'oggetto è quello che raggiungi con la variabile "image" (nel tuo codice). E quindi qual è il problema? Hai già scoperto come ottenere il nome del file a partire dall'oggetto, attraverso "image.cget" (che non so che cosa sia ovviamente, ma è occhei suppongo).


(senza contare, naturalmente, che nel tuo scenario tu *sai già* qual è il nome del file, perché è quello che hai usato per aprire l'immagine in primo luogo... E su due piedi non riesco a immaginare facilmente uno scenario in cui tu non possa semplicemente conservare in una variabile il nome dell'immagine che stai aprendo e risolvere il problema in questro modo, invece di dover recuperare il nome dopo... Però magari invece uno scenario del genere esiste, e tu ne hai bisogno...)








grazie Ric per la risposta, PhotoImage fa parte di tkinter

quello che hai detto è vero, in questo caso il problema non esiste ma come hai ben ipotizzato lo scenario dove si presenta invece si.

che l'oggetto sia "image" siamo d'accordo, tu scrivi: ("pyimage1" non è niente, è solo una stringa di convenienza) quindi secondo te non è una specie di indice/key associata all'oggetto "image" dove sarebbe possibile richiamare i valori in qualche modo?

dico questo essendo che se scrivo:


image1 = PhotoImage(file="photo1.gif")
image2 = PhotoImage(file="photo2.gif")

etc etc

lancio

print(image1, image2, etc, etc)

torna

pyimage1 pyimage2 etc etc


come si vede output del print è una dicitura progressiva quindi secondo te non è una specie di tabella: pyimage1>image1>photo1.gif - pyimage2>image2>photo2.gif

infatti la domanda che ho posto ipotizzava queste due possibilità: se è una stringa allora niente ma se invece non è una stringa ci si può lavorare "credo"

mi è venuto il dubbio essendo che se scrivo: print(type(image)) ritorna <class 'tkinter.PhotoImage'>

grazie ancora

Mah sai, dovresti leggerti la documentazione di PhotoImage per capire se davvero quella stringa è affidabile, ma onestamente non credo che sia nemmeno documentata una cosa del genere. Si dà per scontato che *non* è affidabile, e nel mondo reale nessuno cercherebbe di fare quello che vorresti fare tu. Semplicemente, non è la strada giusta.


Ora, quando fai un print() di un oggetto, invochi il metodo __repr__ di quell'oggetto. Che cosa restituisce __repr__ dipende dall'api dell'oggetto, ma l'idea di base è semplicemente restituire una stringa "amichevole" a scopo di debugging (vedi https://docs.python.org/3/reference/datamodel.html?highlight=__repr__#object.__repr__). Non sta scritto da nessuna parte che questa stringa deve identificare in modo univoco l'oggetto. Per queste cose c'è "id()", o magari "hash()". Poi certo, molto spesso davvero la stringa finisce per essere unica: guarda anche semplicemente questo:


>>> class Bogus: pass
...
>>> a = Bogus()
>>> b = Bogus()
>>> c = Bogus()
>>> a, b, c
(<__main__.Bogus object at 0x00000010CB1BAF28>, 
<__main__.Bogus object at 0x00000010CB1C1470>, 
<__main__.Bogus object at 0x00000010CB1C14A8>)
Come vedi la stringa include l'id dell'oggetto, quindi è univoca. Ma anche in questo caso, come fai a risalire dalla stringa all'oggetto? Intendiamoci, non c'è modo di risalire all'oggetto neppure partendo dal suo id o dal suo hash. Semplicemente, non sono fatti per quello. Il modo giusto per risalire a un oggetto, in Python, è conservarne un riferimento in una variabile.


Nel tuo caso specifico, tu vuoi fare una cosa ancora (leggeremente) più complicata, in verità. Tu vuoi risalire a una *proprietà* dell'oggetto (il nome del file fisico associato all'oggetto) a partire dalla sua rappresentazione-stringa (cioè, la stringa che ottieni con __repr__, come detto). Ovviamente non c'è modo di farlo, perché non c'è modo in primo luogo di risalire all'oggetto, quindi a maggior ragione neppure a una sua proprietà.


Ora, è vero il fatto che, almeno in apparenza, Tkinter mantiene un contatore delle immagini create e quindi restituisce "image1", "image2" etc., quando chiami __repr__ sugli oggetti-immagine che hai aperto. Di nuovo, ti invito a cercare nella documentazione se questa policy è affidabile, e fino a che punto. Per esempio, quando distruggi un oggetto-immagine tkinter potrebbe riciclare il suo numero? Ma anche se dovessi scoprire che questo contatore è "robusto abbastanza", non puoi farci proprio niente comunque.


Cioè, come hai già notato anche tu, potresti tenere traccia dell'*ordine* in cui apri i file, per cui "file1" finisce per essere "image1", e così via. Ma anche lasciando perdere la fragilità della cosa, capisci che stai solo spostando il problema un po' più in là. Adesso il problema è: COME tieni conto dell'ordine in cui apri i file? Per esempio mettendoli in una lista:

file_da_aprire = ['file1.jpg', 'file2.jpg', ...]
for f in file_da aprire:
    ...
Ma appunto, a questo punto HAI GIA' i nomi dei file che ti servono, opportunamente conservati nella tua lista. Perché hai bisogno di recuperarli facendo un giro strano?





> in questo caso il problema non esiste ma come hai ben ipotizzato lo scenario dove si presenta invece si.
Non credo. Magari sbaglio, ma un pizzico di esperienza mi insegna che stai cercando di risolvere un problema semplice senza conoscere il pattern giusto per risolvere questo tipo di problemi. Prova a spiegare che cosa vuoi fare davvero.








Post-scriptum, solo per il gusto di aggiungere una nota un po' difficile e anche un po' sbruffona. Prima ho scritto che non c'è modo di risalire all'oggetto partendo dal suo id. Ma non è completamente vero. Almeno in C-Python, l'id di un oggetto è in effetti l'indirizzo di memoria in cui risiede l'oggetto:


>>> class Bogus: pass
...
>>> a = Bogus()
>>> id(a)
72127091992
Questo vuol dire che in effetti è possibile risalire dall'id all'oggetto... *non* usando Python... ma usando C (da dentro Python)!


>>> import ctypes
>>> b = ctypes.cast(id(a), ctypes.py_object).value
>>> id(b)
72127091992
>>> b is a
True
Buffo, vero? Ma ovviamente lascia perdere questa cosa, non ha senso per quello che vuoi fare tu. Era solo per far vedere qualcosa di inconsueto.
ancora grazie per la risposta Ric, sei stato molto chiaro nella spiegazione

Questo vuol dire che in effetti è possibile risalire dall'id all'oggetto... *non* usando Python... ma usando C (da dentro Python)!


assolutamente Ric, lunge da me questo pensiero ahahahah per me python già è oltre figuriamoci il linguaggio C


file_da_aprire = ['file1.jpg', 'file2.jpg', ...]



si in effetti alla lista ci ero arrivato, ed infatti avevo già realizzato come "riuscire" a portare a casa il risultato. nel mio "piccolo" sò che più si pasticcia e più sorgono problemi (come hai sottolineato anche tu)

in questo caso il problema non esiste ma come hai ben ipotizzato lo scenario dove si presenta invece si.

Non credo. Magari sbaglio, ma un pizzico di esperienza mi insegna che stai cercando di risolvere un problema semplice senza conoscere il pattern giusto per risolvere questo tipo di problemi. Prova a spiegare che cosa vuoi fare davvero.



ecco il codice incriminato (funziona ma anch'io per gli stessi motivi che hai menzionato non sono proprio contento quando sono abbligato a manipolare le stringhe per ottenere il risultato voluto)

def cmd():
    chc = random.choice(img)
    can.itemconfig(log, image=chc)

    print(can.itemcget(log, "image"))
    print(img[int(str(chc)[7:])-1].cget("file"))

img = [PhotoImage(file="a.gif"), PhotoImage(file="b.gif")]
can = Canvas(root, width=300, height=300, bg="white")
log = can.create_image(151, 151, image=None)


ovviamente come si nota in questo codice ho messo i files in una lista mentre nel codice del post iniziale ho volutamente fare l'esempio con due file immagine associati a due variabili diverse essendo che in quel caso il "giochetto" della manipolazione del testo tramite indice non si poteva fare e quindi "speravo" in una gestione tramite qualche funzione o metodo incorporato. in pratica sarei stato contento se si poteva realizzare una cosa simile:

print(img0)
ritorna pyimage1

print(img0.cget("file"))
ritorna a.gif

print(can.itemcget(log, "image"))
ritorna pyimage1

print(can.itemcget(log, "image").cget("file"))
"ritornasse" a.gif



da notare, anche se il risultato è lo stesso essendo che entrambi
da soli estraggono lo stesso valore "pyimage1" come si vede sopra
mentre lanciando il print ed inserendoli nel type il discorso cambia

print(type(img0)) ritorna <class 'tkinter.PhotoImage'> 

print(type(can.itemcget(log, "image"))) ritorna <class 'str'>


e credo sia questo il motivo per cui nel secondo esempio non funziona essendo una semplice stringa
mentre nel primo esempio l'oggetto risulta una photoimage di tkinter dove posso usare ".cget("file")"


l'ipotesi era quella che PhotoImage fosse una specie di raccoglitore di immagini e che le memorizzasse tipo database come ho detto prima tipo "image1>photo1.gif>pyimage1" e così via come una specie di dizionario, ma quando ho costatato (come anche tu hai ipotizzato) che la documentazione al riguardo è scarsa se no proprio nulla, ho deciso di chiedere aiuto essendo che non riuscendo a venirne a capo mi sono chiesto "se si potesse fare".

grazie Ric per la disponibilità e oltre a quanto postato se hai qualcosa da aggiungere come chiarimento o suggerimenti sono tutto orecchie :)
Post-scriptum, solo per il gusto di aggiungere una nota un po' difficile e anche un po' sbruffona. Prima ho scritto che non c'è modo di risalire all'oggetto partendo dal suo id. Ma non è completamente vero. Almeno in C-Python, l'id di un oggetto è in effetti l'indirizzo di memoria in cui risiede l'oggetto:


>>> class Bogus: pass
...
>>> a = Bogus()
>>> id(a)
72127091992
Questo vuol dire che in effetti è possibile risalire dall'id all'oggetto... *non* usando Python... ma usando C (da dentro Python)!


>>> import ctypes
>>> b = ctypes.cast(id(a), ctypes.py_object).value
>>> id(b)
72127091992
>>> b is a
True
Buffo, vero? Ma ovviamente lascia perdere questa cosa, non ha senso per quello che vuoi fare tu. Era solo per far vedere qualcosa di inconsueto.
Sei Una Persona Malvagia™, lo sai vero? :D

THE 🍺-WARE LICENSE (Revision ㊷):
<㎝🐌🐍.🇮🇹> wrote this post. As long as you retain this notice you
can do whatever you want with this stuff. If we meet some day, and you
think this stuff is worth it, you can buy me a 🍺 in return. -- ㎝
Guarda, abbi pazienza ma è che proprio stai facendo un'insalata di concetti diversi. Confondi le cose, non sei preciso. Intanto liberati per prima cosa di quei "print". Non usare più "print", non pensare più a "print", lascia perdere "print". Questo "print" è una delle prime cose che i principianti imparano (o credono di imparare) ed è anche la singola cosa più dannosa che rovina la comprensione di un principiante. Non puoi confondere un riferimento a un oggetto con la stringa che l'oggetto emette in risposta a un __repr__() (e quindi a un print). Quella stringa non è un riferimento all'oggetto, è solo... decorazione, niente.


Come seconda cosa, lascia perdere anche tkinter. Finché non hai chiaro che cos'è una variabile, che cos'è un oggetto, come si usano gli oggetti... non so, stai andando a tentoni invece di procedere per gradi. Per esempio, quando scrivi

> img = [PhotoImage(file="a.gif"), PhotoImage(file="b.gif")]
> (...)
> come si nota in questo codice ho messo i files in una lista

Ma no!, come si nota in questo codice hai messo in una lista *gli oggetti PhotoImage* che contengono i file, non i file. Siccome qui stiamo parlando di come risalire dal nome di un file agli oggetti e viceversa, confondere le due cose è parecchio grave, capisci. Eccetera eccetera.





Ora ti spiego il problema se vuoi, ma il fatto è che temo che ti mancano le basi per comprendere quello che ti spiego. Quindi probabilmente crederai di aver capito, e continuerai ad andare a tentoni. Davvero, la soluzione è prendersi un buon libro e seguirlo daccapo passo-passo.


In ogni caso, il problema è questo. Tu hai un oggetto-Risorsa, e poi un oggetto-Manager che "acquisisce" la Risorsa, diciamo così. In pratica, ciascuna Risorsa sta "dentro" il suo Manager. Il problema è:
1) ho in mano un riferimento al Manager, voglio ricavare un riferimento alla Risorsa che contiene;
2) viceversa, ho in mano una Risorsa, voglio sapere il Manager che la contiene.

La prima parte del problema in genere è più semplice: si suppone che il Manager "sa" quale Risorsa sta gestendo, e quindi probabilmente ha anche un metodo già pronto per sputare fuori un riferimento alla risorsa. Se stai usano una classe-Manager scritta da altri (per esempio, all'interno di un framework come le tk) allora ti basta leggere la documentazione per trovare quel metodo (per esempio, abbiamo visto che esiste PhotoImage.cget). Se invece la classe te la stai facendo tu, allora ti conviene scrivertelo, un metodo del genere. Qualcosa come:


class Manager:
    def __init__(self, risorsa):
        self.risorsa = risorsa

    def get_risorsa(self):
        return self.risorsa

# uso:
risorsa = 'io sono una Risorsa' # un qualunque oggetto-Risorsa
manager = Manager(risorsa)      # un oggetto-Manager che "contiene" la Risorsa
r = manager.get_risorsa() # restituisce un riferimento alla Risorsa usata
r is risorsa # è True: il riferimento ottenuto è davvero quello alla Risorsa usata
La seconda parte (risalire dalla Risorsa al Manager) è ovviamente più difficile. Se il Manager "sa" quale Risorsa contiene, viceversa la Risorsa esiste da prima che il suo Manager venga creato, e quindi non può "sapere" in quale Manager finirà. Ora, naturalmente se tu hai solo un Manager e una Risorsa, la soluzione è banale: ti basta mantenere in vita le variabili che si riferiscono a questi due oggetti (nell'esempio sopra "risorsa" e "manager"), e poi tu lo sai già che "quel" Manager contiene "quella" Risorsa.
Ma se le cose diventano più "dinamiche", allora si complicano. In questi casi la soluzione è mantenere una struttura-dati parallela, una specie di registro dove annoti man mano quali Risorse sono contenute dentro quali Manager. Che cosa è questo "registro"? Mah, quello che vuoi, dipende dalle tue esigenze. Nei casi più semplici, un dizionario è la prima cosa che viene in mente, e in effetti può andar bene.


Facciamo un esempio. Abbiamo una serie di Risorse, di cui non conosciamo neanche il numero esatto, perché le prendiamo da una sorgente esterna al nostro controllo (le carichiamo da un file preparato dall'utente, o da un database, va a sapere). Supponiamo, per capirci, che le nostre Risorse siano le righe di testo di un file esterno (ogni riga è una Risorsa). Quindi apriamo il file e carichiamo ogni riga in un oggetto-Manager (usiamo la classe Manager che ho scritto sopra):
with open('file_delle_risorse', 'r') as f:
    for line in f:
        manager = Manager(line)
Con un codice del genere abbiamo ovviamente due problemi: il primo è che non stiamo conservando *nessun* riferimento né ai Manager né alle Risorse. A ogni ciclo del "for", la variabile "line" si riferisce alla Risorsa, e "manager" si riferisce al Manager: ma al ciclo successivo, "line" e "manager" si riferiscono a una nuova Risorsa e a un nuovo Manager, e i precedenti diventano irraggiungibili e vengono distrutti. Quindi in pratica stiamo distruggendo il lavoro man mano che lo facciamo. Alla fine del ciclo, resteranno in vita solo l'ultima Risorsa e l'ultimo Manager creati. Del resto, non è che possiamo usare una variabile per ciascun Manager, come prima:
manager1 = Manager(line1)
manager2 = Manager(line2)
...
perché semplicemente non sappiamo quante sono le linee del file, quindi quante sono le Risorse, quindi quanti sono i Manager da creare. Il secondo problema è quello che dicevamo: non sappiamo tener traccia dei collegamenti tra Manager e Risorse, e in particolare risalire da una Risorsa a un Manager (l'opposto è più facile, come abbiamo visto).
Ed ecco che una struttura-dati separata (per esempio un dizionario) può risolvere entrambi i nostri problemi:
registro = {}
with open('file_delle_risorse', 'r') as f:
    for line in f:
        manager = Manager(line)
        registro\[line\] = manager    # scusa il \[ 
In questo modo dentro il registro conserviamo i riferimenti sia alle Risorse (che sono le chiavi del dizionario) sia ai Manager (che sono i valori). Inoltre, conserviamo l'associazione Risorsa->Manager che ci interessa. Se per esempio abbiamo una Risorsa che si chiama "pippo", per risalire al Manager che la contiene basta fare:
risorsa = 'pippo' # sappiamo che una delle risorse è "pippo"
manager = registro\[risorsa\] # adesso "manager" è un riferimento al Manager di "pippo"
# e viceversa...
r = manager.get_risorsa() # ottengo dal Manager un riferimento alla Risorsa contenuta
r is risorsa # è True
Non è detto che un dizionario sia la struttura-dati migliore per contenere questo registro. Dipende dal caso specifico. Per esempio, se sei in un contesto in cui ti interessa di più *l'ordine* in cui ti arrivano le Risorse e quindi sono creati i Manager corrispondenti, allora potresti tenere una lista, o anche una doppia lista:
registro_manager = []
registro_risorse = []
with open('file_delle_risorse', 'r') as f:
    for line in f:
        manager = Manager(line)
        registro_manager.append(manager)
        registro_risorse.append(line)
E adesso, se la tua situazione è tale per cui ti interessa sapere qual è, poniamo, il terzo Manager e/o la terza Risorsa creata, puoi banalmente fare:
terzo_manager = registro_manager[ 2 ]
terza_risorsa = registro_risorse[ 2 ]
E ci sono molte altre soluzioni possibili, a seconda di cosa conviene nei vari casi. E ovviamente tutte queste soluzioni hanno dei problemi e delle fragilità (che cosa succede se elimino un Manager, o se ne aggiungo uno? e se un Manager cambia Risorsa a run-time? eccetera). In generale, questo è un problema di implementare un pattern MCV: questo "registro", comunque tu lo realizzi, è in sostanza un "controller" che media tra gli oggetti presenti. In senso astratto, il controller è una classe (o una serie di classi) su cui deve essere possibile fare certe operazioni, e che devono garantire una certa robustezza. Per esempio, se volessi davvero implementare il tuo registro come una lista doppia, allora sicuramente tenere due liste "sciolte" nel codice è molto fragile: per esempio, se cancelli un Manager devi sempre ricordarti di cancellare anche la Risorsa corrispondente. Allora vorrai piuttosto "inscatolare" questa doppia lista in una classe specializzata che si curi di implementare in modo sicuro le operazioni richieste:
class Registro:
    def __init__(self):
        self.registro_risorse = []
        self.registro_manager = []
    def aggiungi(self, manager, risorsa):
        self.registro_risorse.append(risorsa)
        self.registro_manager.append(manager)
    def elimina(self, n):
        self.registro_risorse.remove(n)
        self.registro_manager.remove(n)
    ... etc. etc. ...


E poco per volta questo diventa un serio esercizio di programmazione a oggetti.


PS: scusa l'uso di "\[" e "\]" per dire "[" e "]"... il fatto è che per qualche ragione questo autentico cess* di motore di rendering del forum si intestardisce a creare automaticamente voci inutili dell'inutile wiki.... immagino che nessuno riparerà più questo baco, ma è veramente una seccatura.






--- Ultima modifica di RicPol in data 2018-10-12 15:44:22 ---
Ric complimenti per tutte le nozioni che hai discusso che sono molto tecniche e quindi non facili

ricordo che quando mi sono presentato l'ho fatto come novizio e quindi spero che tollererai le mie inesattezze nei termini che ho fatto (e che farò)

anche se è vero che in genere tendo a non specificare i tecnicismi sia per poca conoscenza ma anche per il fatto che do per "scontato" alcune cose




tutto ciò che hai detto non posso che darti ragione, ma volevo solo sottolineare che la soluzione da te presentata sono daccordo che sia migliore

gestire le Risorse/Manager etc per carità tutto molto bello ma a parte che come hai anticipato anche queste soluzioni hanno dei problemi e delle fragilità

e che quindi bisogna poi tenerne conto e risolverle. in sostanza dovrei scrivere un codice che faccia quello per cui ho chiesto se esistesse un modo per farlo

ovviamente entrambi sappiamo che non riuscirei a fare una cosa simile se no l'ho avrei fatto senza dedicare molte ore a cercare una funzione/metodo inesistente

sono consapevole delle mie conoscenze e capacità e sopratutto di quello che mi può tornare utile realizzare sempre nell'ambito amatoriale di certo no professionale




ovviamente detto questo dico anche che se da qualche tempo mi sono avvicinato a Python è perchè ho voluto ampliare le mie conoscenze ed andare avanti


essendo che come giusto che sia se non si ha voglia di progredire in certi ambiti è meglio non metterci il naso, e quindi a tale proposito quale libro cosiglieresti?



ps grazie della spiegazione delle parentesi quadre :ok:



mi è venuto il dubbio se nel caso il modulo PIL abbia già qualche funzionalità nativà per tale scopo....


--- Ultima modifica di pypy in data 2018-10-13 02:10:51 ---
Sai, il problema non è essere principianti (e ci mancherebbe). Il problema è essere principianti e voler fare cose da non-principianti. Il principiante impara che cosa è una lista python, per dire, e dice "ok, sono pronto: adesso faccio un'intelligenza artificiale che trasforma frasi italiane in azioni disegnate" (non scherzo, c'è davvero un thread del genere qui).


Occorre andare per gradi, con calma e molta pazienza. E' ovvio che ti vengono in mente decine di applicazioni pratiche da fare "subito", ma non c'è niente da fare: dopo aver imparato la lista, impara il dizionario (per dire). In particolare, ogni cosa che riguarda una interfaccia grafica richiede nozioni di programmazione a oggetti. Sì, è vero che puoi abborracciare una finestra in tkinter così alla buona, un po' copiando in giro. Ma al primo ostacolo "da mondo reale" sei già in acque profonde. Naturalmente non è che uno debba leggersi tutto il GOF prima di affrontare la prima interfaccia grafica della sua vita, eh. Ma almeno avere un po' di dimestichezza con le variabili, le funzioni, le classi, i metodi.
Tra l'altro, la spiegazione che ti ho dato è già molto semplificata e tagliata sul tuo caso specifico. In generale, il problema dei rapporti tra oggetti è una questione di design pattern complessa. Ma non è il forum la sede per imparare queste cose. Hai già visto quante parole ho dovuto metterci per spiegarti questa piccola questione.

Purtroppo la tragica verità è che imparare a programmare è frustrante, non è divertente. O per lo meno, bisogna imparare a divertirsi con poco, per un bel po' di tempo. E' come un gioco di ruolo alle prime avventure: tu *sai* che è possibile castare magie del nono livello e andare a caccia di draghi, ma nel frattempo devi accontentarti di dare la caccia ai goblin e castare magic missile.





> mi è venuto il dubbio se nel caso il modulo PIL abbia già qualche funzionalità nativà per tale scopo....
Beh, certo che sì. Una volta che hai prodotto un oggetto PIL.Image caricandoci dentro un file immagine, puoi usare PIL.Image.filename per ri-ottenere il nome del file che ci hai caricato dentro: https://pillow.readthedocs.io/en/5.3.x/reference/Image.html#PIL.Image.filename (beh, certo: ovviamente quello *non* è l'oggetto-file, è solo la stringa-path del file... ma da quello hai comunque le informazioni necessarie per ri-aprire l'oggetto-file, se vuoi).



--- Ultima modifica di RicPol in data 2018-10-13 09:42:38 ---
PS: scusa l'uso di "\[" e "\]" per dire "[" e "]"... il fatto è che per qualche ragione questo autentico cess* di motore di rendering del forum si intestardisce a creare automaticamente voci inutili dell'inutile wiki.... immagino che nessuno riparerà più questo baco, ma è veramente una seccatura.

Sì, il motore è un cesso, però sia per il CamelCase che per altro, usa una \ davanti alla parte incriminata (e solo davanti a questa).

Così CamelCase diventa CamelCase e risorsaqualcosa diventa risorsa[qualcosa].

Cya



Pagina: 1 2 Avanti



Esegui il login per scrivere una risposta.