Maybe "kind-of" monad in Python Maybe "kind-of" monad in Python python python

Maybe "kind-of" monad in Python


company = country = Nonetry:    person  =  Person.find(id=12345)    company = Company.find(person.companyId)    country = Country.find(company.countryId)except AttributeError:    pass # `person` or `company` might be None

EAFP


Exploit the short-circuit behavior and that a custom object is true by default and None is false:

person  = Person.find(id=12345)company = person and person.companycountry = company and company.country


Python does not have a particularly nice syntax for monads. That being said, if you want to limit yourself to using something like the Maybe monad (Meaning that you'll only be able to use Maybe; you won't be able to make generic functions that deal with any monad), you can use the following approach:

class Maybe():    def andThen(self, action): # equivalent to Haskell's >>=        if self.__class__ == _Maybe__Nothing:            return Nothing        elif self.__class__ == Just:            return action(self.value)    def followedBy(self, action): # equivalent to Haskell's >>        return self.andThen(lambda _: action)class _Maybe__Nothing(Maybe):    def __repr__(self):        return "Nothing"Nothing = _Maybe__Nothing()class Just(Maybe):    def __init__(self, v):        self.value = v    def __repr__(self):        return "Just(%r)" % self.value

Then, make all of the methods that currently return None return either Just(value) or Nothing instead. This allows you to write this code:

Person.find(id=12345)    .andThen(lambda person: Company.find(person.companyId))    .andThen(lambda company: Country.find(company.countryId))

You can of course adapt the lambdas to store the intermediate results in variables; it's up to you how to do that properly.