[Python-Dev] GeneratorExit inheriting from Exception

Nick Coghlan ncoghlan at gmail.com
Mon Mar 20 10:19:01 CET 2006


Raymond Hettinger wrote:
> While Guido is thinking, could one of the proponents please enumerate the 
> reasons for treating GeneratorExit like KeyboardInterrupt and SystemExit.
> 
> To me, they obviously should be under Exception, and not treated like 
> KeyboardInterrupt or SystemExit, so that probably means that I'm missing 
> something about GeneratorExit.

If GeneratorExit *isn't* special, then correct catch-all exception handling 
around a yield expression in a generator looks like:

   def run_tasks(tasks, failed_tasks)
       for task in tasks:
           try:
               yield task()
           except GeneratorExit:  # don't break gen.close()
               raise
           except Exception:
               failed_tasks.append((task, sys.exc_info()))


Having to explicitly reraise a terminating exception like that is the exact 
idiom we're trying to get rid of for SystemExit and KeyboardInterrupt, so it 
makes sense to me to avoid it for GeneratorExit as well.

Given that the default system-level excepthook *won't* ignore GeneratorExit 
(and so an error message will still be printed), I see moving it out with the 
other two terminating exceptions as the best option. The only way for that 
approach to do the wrong thing is if GeneratorExit is raised outside a 
generator's pseudothread, at which point I'd be blaming the code that raised 
it explicitly (the interpreter core only ever raises it as a result of a call 
to gen.close()).

Note that this argument does *not* apply to StopIteration - that should stay 
under Exception because it should never accidentally leak beyond the code that 
is calling the next() method.

Cheers,
Nick.

-- 
Nick Coghlan   |   ncoghlan at gmail.com   |   Brisbane, Australia
---------------------------------------------------------------
             http://www.boredomandlaziness.org


More information about the Python-Dev mailing list