Seriously though, not being able to define a serialization method can be a limitation. However, it is always possible to turn a generator into an iterator class with whatever methods you like, but the code may end up looking totally different.
So yeah, you can write a custom class. But you will need to add a custom "save state" and "load state" in your class' __iter__ method. So all the benefits go away.
It should be possible to create the exact same classes dynamically, without using exec. The only advantage I can see of the exec is that the class template string makes it a little clearer what the equivalent "normal" class definition would look like.
There are other drawbacks to exec though, some people have disabled exec for security reasons and it's opaque to things like pypy.
The usual #python response to people using the array module was to instead consider NumPy (with its excellent arrays) or use normal lists and PyPy to make it fast.
The same conversion for the later examples with multiple yield statements, try: except: or try: finally: will be much hairier, though.