Re: [Python-Dev] anonymous blocks (don't combine them with generator finalization)

2005-04-21 Thread Josiah Carlson

Guido van Rossum [EMAIL PROTECTED] wrote:
 
 [Brett]
  I think I agree with Samuele that it would be more pertinent to put all of 
  this
  effort into trying to come up with some way to handle cleanup in a 
  generator.
 
 I.e. PEP 325.
 
 But (as I explained, and you agree) that still doesn't render PEP 310
 unnecessary, because abusing the for-loop for implied cleanup
 semantics is ugly and expensive, and would change generator semantics;
 and it bugs me that the finally clause's reachability depends on the
 destructor executing.

Yes and no.  PEP 325 offers a method to generators that handles cleanup
if necessary and calls it close().  Obviously calling it close is a
mistake.  Actually, calling it anything is a mistake, and trying to
combine try/finally handling in generators with __exit__/close (inside
or outside of generators) is also a mistake.


Start by saying, If a non-finalized generator is garbage collected, it
will be finalized.  Whether this be by an exception or forcing a return,
so be it.

If this were to happen, we have generator finalization handled by the
garbage collector, and don't need to translate /any/ for loop.  As long
as the garbage collection requirement is documented, we are covered (yay!).


What about ...

i.__enter__()
try:
...
finally:
i.__exit__()

... types of things?  Well, you seem to have offered a syntax ...

[VAR '=']* EXPR:
BODY

... which seems to translate into ...

[VAR = ] __var = EXPR
try:
BODY
finally:
__var.__exit__()

... or something like that.  Great!  We've got a syntax for resource
allocation/freeing outside of generators, and a non-syntax for resource
allocation/freeing inside of generators.


 - Josiah

___
Python-Dev mailing list
Python-Dev@python.org
http://mail.python.org/mailman/listinfo/python-dev
Unsubscribe: 
http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com


Re: [Python-Dev] anonymous blocks (don't combine them with generator finalization)

2005-04-21 Thread Bob Ippolito
On Apr 21, 2005, at 8:59 PM, Josiah Carlson wrote:
Guido van Rossum [EMAIL PROTECTED] wrote:
[Brett]
I think I agree with Samuele that it would be more pertinent to put 
all of this
effort into trying to come up with some way to handle cleanup in a 
generator.
I.e. PEP 325.
But (as I explained, and you agree) that still doesn't render PEP 310
unnecessary, because abusing the for-loop for implied cleanup
semantics is ugly and expensive, and would change generator semantics;
and it bugs me that the finally clause's reachability depends on the
destructor executing.
Yes and no.  PEP 325 offers a method to generators that handles cleanup
if necessary and calls it close().  Obviously calling it close is a
mistake.  Actually, calling it anything is a mistake, and trying to
combine try/finally handling in generators with __exit__/close (inside
or outside of generators) is also a mistake.
Start by saying, If a non-finalized generator is garbage collected, it
will be finalized.  Whether this be by an exception or forcing a 
return,
so be it.

If this were to happen, we have generator finalization handled by the
garbage collector, and don't need to translate /any/ for loop.  As long
as the garbage collection requirement is documented, we are covered 
(yay!).
Well, for the CPython implementation, couldn't you get away with using 
garbage collection to do everything?  Maybe I'm missing something..

import weakref
class ResourceHandle(object):
def __init__(self, acquire, release):
acquire()
# if I understand correctly, this is safer than __del__
self.ref = weakref.ref(self, lambda o:release())
class FakeLock(object):
def acquire(self):
print acquired
def release(self):
print released
def with_lock(lock):
r = ResourceHandle(lock.acquire, lock.release)
yield None
del r
 x = with_lock(FakeLock())
 del x
 with_lock(FakeLock()).next()
acquired
released
 for ignore in with_lock(FakeLock()):
... print ignore
...
acquired
None
released
I could imagine someone complaining about generators that are never 
used missing out on the acquire/release.  That could be solved with a 
trivial rewrite:

def with_lock(lock):
def _with_lock(r):
yield None
del r
return _with_lock(ResourceHandle(lock.acquire, lock.release))
 x = with_lock(FakeLock())
acquired
 del x
released
Of course, this just exaggerates Guido's it bugs me that the finally 
clause's reachability depends on the destructor executing.. but it 
does work, in CPython.

It seems to me that this pattern would be painless enough to use 
without a syntax change...

-bob
___
Python-Dev mailing list
Python-Dev@python.org
http://mail.python.org/mailman/listinfo/python-dev
Unsubscribe: 
http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com


Re: [Python-Dev] anonymous blocks (don't combine them with generator finalization)

2005-04-21 Thread Brett C.
Bob Ippolito wrote:
 
 On Apr 21, 2005, at 8:59 PM, Josiah Carlson wrote:
 
 Guido van Rossum [EMAIL PROTECTED] wrote:


 [Brett]

 I think I agree with Samuele that it would be more pertinent to put
 all of this
 effort into trying to come up with some way to handle cleanup in a
 generator.


 I.e. PEP 325.

 But (as I explained, and you agree) that still doesn't render PEP 310
 unnecessary, because abusing the for-loop for implied cleanup
 semantics is ugly and expensive, and would change generator semantics;
 and it bugs me that the finally clause's reachability depends on the
 destructor executing.


 Yes and no.  PEP 325 offers a method to generators that handles cleanup
 if necessary and calls it close().  Obviously calling it close is a
 mistake.  Actually, calling it anything is a mistake, and trying to
 combine try/finally handling in generators with __exit__/close (inside
 or outside of generators) is also a mistake.


 Start by saying, If a non-finalized generator is garbage collected, it
 will be finalized.  Whether this be by an exception or forcing a return,
 so be it.

 If this were to happen, we have generator finalization handled by the
 garbage collector, and don't need to translate /any/ for loop.  As long
 as the garbage collection requirement is documented, we are covered
 (yay!).
 
 
 Well, for the CPython implementation, couldn't you get away with using
 garbage collection to do everything?  Maybe I'm missing something..
 

[SNIP]

Well, if you are missing something then so am I since your suggestion is
basically correct.  The only issue is that people will want more immediate
execution of the cleanup code which gc cannot guarantee.  That's why the
ability to call a method with the PEP 325 approach gets rid of that worry.

-Brett
___
Python-Dev mailing list
Python-Dev@python.org
http://mail.python.org/mailman/listinfo/python-dev
Unsubscribe: 
http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com


Re: [Python-Dev] anonymous blocks (don't combine them with generator finalization)

2005-04-21 Thread Bob Ippolito
On Apr 22, 2005, at 12:28 AM, Brett C. wrote:
Bob Ippolito wrote:
On Apr 21, 2005, at 8:59 PM, Josiah Carlson wrote:
Guido van Rossum [EMAIL PROTECTED] wrote:
[Brett]
I think I agree with Samuele that it would be more pertinent to put
all of this
effort into trying to come up with some way to handle cleanup in a
generator.

I.e. PEP 325.
But (as I explained, and you agree) that still doesn't render PEP 
310
unnecessary, because abusing the for-loop for implied cleanup
semantics is ugly and expensive, and would change generator 
semantics;
and it bugs me that the finally clause's reachability depends on the
destructor executing.

Yes and no.  PEP 325 offers a method to generators that handles 
cleanup
if necessary and calls it close().  Obviously calling it close is a
mistake.  Actually, calling it anything is a mistake, and trying to
combine try/finally handling in generators with __exit__/close 
(inside
or outside of generators) is also a mistake.

Start by saying, If a non-finalized generator is garbage collected, 
it
will be finalized.  Whether this be by an exception or forcing a 
return,
so be it.

If this were to happen, we have generator finalization handled by the
garbage collector, and don't need to translate /any/ for loop.  As 
long
as the garbage collection requirement is documented, we are covered
(yay!).

Well, for the CPython implementation, couldn't you get away with using
garbage collection to do everything?  Maybe I'm missing something..
[SNIP]
Well, if you are missing something then so am I since your suggestion 
is
basically correct.  The only issue is that people will want more 
immediate
execution of the cleanup code which gc cannot guarantee.  That's why 
the
ability to call a method with the PEP 325 approach gets rid of that 
worry.
Well in CPython, if you are never assigning the generator to any local 
or global, then you should be guaranteed that it gets cleaned up at the 
right time unless it's alive in a traceback somewhere (maybe you WANT 
it to be!) or some insane trace hook keeps too many references to 
frames around..

It seems *reasonably* certain that for reasonable uses this solution 
WILL clean it up optimistically.

-bob
___
Python-Dev mailing list
Python-Dev@python.org
http://mail.python.org/mailman/listinfo/python-dev
Unsubscribe: 
http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com