iteradores.

Joaquin Jose del Cerro Murciano jjdelcerromurciano en yahoo.es
Vie Mayo 20 22:14:01 CEST 2005


Muchas gracias por tu respuesta. Conozco algo sobre compiladores he 
interpretes y cuando me ha pasado ya intuia que era una putada gorda de 
resolver para el interprete, pero lo que mas agrdezco es que me has ofrecido 
la respuesta, y ademas simple como un botijo y en la que ante la perplejidad 
de pete no habia caido. Algo tan simple como implementar mi metodo next que 
lo gestione.

Una cosa mas, "corutina". Se puede explicar en dos parrafos lo que es eso ? Si 
es muy largo, puedes pasarme alguna direccion para leer que lo explique 
aceptablemente ? Ya me he tropecedo con ello algunas veces y no tengo claro 
de que me hablan.

Me resistia a apuntarme a las lista de python en ingles por que no lo leo con 
demasiada soltura y me es imposible escribirlo, pero por lo que veo me voy a 
tener que suscribir para estar al dia de lo que hacen con el interprete.

Un saludo 
Joaquin.


El Friday, 20 de May de 2005 21:56, Hernan Martinez Foffani escribió:
> > ...
> > Y para mi sorpresa inicial el compiler se niega a compilar
> > el __iter__ diciendo que no puedo user try-finally con un yield
> > dentro. Lo piensas friamente y acabas viendole cierta logica. Parece
> > que manda cojones implementar eso.
>
> Nones...  No se puede.
> Casualmente los desarrolladores de python estan conversando
> sobre precisamente esto mismo. (Ahora mismo hay un hilo de
> conversacion de chiquicientos mil mensajes...)
>
> > Asi que decido cambiar  el __iter__ por este otro:
> >
> >   def __iter__(self):
> >     try:
> >       self._lock.acquire()
> >       for key in dict.iterkeys(self):
> >         yield key
> >     except:
> >       print "### __iter__: Ha petao"
> >       self._lock.release()
> >       raise
> >
> > Asi parece que compila y asta parece funcionar. Pero solo parece
> > funcionar. Mi intencion era que mientras que en un thread  este
> > iterando sobre el diccionario, ningun otro thread le toque las
> > narices al diccionario, y que si en ese bucle algo peta me liberase
> > el bloqueo sobre el diccionario. Algo inocente y aparentemente
> > deseable.
> >
> > Pos va a se r que no.
> > No va.
> > Si ejecuto el codigo siguiente el resultado es, para mi, del todo
> > sorprendente.
> >
> > d = SynchronizedDict()
> > d["a"] = 1
> > d["b"]  = 2
> > d["c"] = 3
> > try:
> >   for x in d:
> >      1/0
> > except:
> >    print "### Peto."
> >
> > El resultado que esperaba era algo como
> >
> > ### __iter__: Ha petao
> > ### Peto.
> >
> > Pero solo sale
> >
> > ### Peto.
> >
> > Y ademas me deja el RLock pillado.
>
> Je... claro.  Lo que pasa es que no se le puede pasar
> una excepcion de vuelta a un generador.  De hecho, por el
> momento, no se le puede devolver nada.
>
> > ...
> > Si alguien ha ententido lo que quiero y sabe indicarme por donde
> > meterle mano se lo agradeceria, no es que sea una cuestion de vida o
> > muerte, simplemente me ha tocado llamar a d.acquire() y d.release()
> > antes y despues de iterar sobre el diccionario  en todo el codigo de
> > la aplciacion, cosa que ya he hecho, pero me parece un poco bruto
> > cuando aparentaba haber una solucion simple al alcance de la mano.
>
> No eres el unico.
>
> Lo que en realidad estas haciendo es intentar convertir un
> iterador (generador extrictamente hablando) en una corutina.
> Es tentador, pero por el momento los generadores no llegan a
> tanto.
>
> Hay varias posibilidades en estudio y quizas es posible que se
> implementen muchas de ellas.  Una es la que mencionaste antes:
> try/yield/finally, que tambien puede servir para transacciones.
> Otra es un protocolo para clases __enter__ y __exit__.
> Un nuevo tipo de sentencia python que haga uso de cualquiera
> de ambas posibilidades.  Algo como:
>
>   with tran(db):
>       db.insert("un registro")
>       db.insert("otro")
>
> Por ahora paciencia, pero habra novedades...
>
> En cuanto a tu problema especifico entiendo que lo puedes resolver
> sin usar el yield y creando un iterador que tenga el metodo next(),
> que lleve la cuenta de por donde va y que dispare StopIteration
> cuando llega al final, llamando adquire y release segun tu
> conveniencia.
>
> Saludos,
> -H.




Más información sobre la lista de distribución Python-es