Note that there are some explanatory texts on larger screens.

plurals
  1. POpython: mutating `globals` to dynamically put things in scope
    primarykey
    data
    text
    <p>how terrible an idea is this? class <code>monad</code> implements the <code>with</code> interface to put things in and out of scope, so i can write a library of generic functions like m_chain who refer to functions <code>unit</code> and <code>bind</code> who can have an implementation put in at runtime. (It doesn't matter what all this code does or if it's a good idea.)</p> <p>other ideas i tried all revolved around passing around a structure containing unit/bind as an argument or a kwarg, or putting m_chain in a class, implement it in terms of self.unit and self.bind and having derived classes provide them. but it added complexity to the code and syntax and tied unit/bind to the way monads are expressed in python. using scope for this just feels so much nicer.</p> <pre><code>class monad: """Effectively, put the monad definition in lexical scope. Can't modify the execution environment `globals()` directly, because after globals().clear() you can't do anything. """ def __init__(self, monad): self.monad = monad self.oldglobals = {} def __enter__(self): for k in self.monad: if k in globals(): self.oldglobals[k]=globals()[k] globals()[k]=self.monad[k] def __exit__(self, type, value, traceback): """careful to distinguish between None and undefined. remove the values we added, then restore the old value only if it ever existed""" for k in self.monad: del globals()[k] for k in self.oldglobals: globals()[k]=self.oldglobals[k] def m_chain(*fns): """returns a function of one argument which performs the monadic composition of fns""" def m_chain_link(chain_expr, step): return lambda v: bind(chain_expr(v), step) return reduce(m_chain_link, fns, unit) identity_m = { 'bind':lambda v,f:f(v), 'unit':lambda v:v } with monad(identity_m): assert m_chain(lambda x:2*x, lambda x:2*x)(2) == 8 maybe_m = { 'bind':lambda v,f:f(v) if v else None, 'unit':lambda v:v } with monad(maybe_m): assert m_chain(lambda x:2*x, lambda x:2*x)(2) == 8 assert m_chain(lambda x:None, lambda x:2*x)(2) == None </code></pre>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload