On Sun, Sep 20, 2015 at 12:05:52PM +0100, Paul Moore wrote:
On 20 September 2015 at 08:31, Steven D'Aprano
wrote: I'm not convinced that we should generalise this beyond the three original examples of attribute access, item lookup and function call. I think that applying ? to arbitrary operators is a case of "YAGNI". Or perhaps, "You Shouldn't Need It".
Agreed.
Does this need to be an operator? How about the following:
Sadly, I think it does. Guido has (I think) ruled out the Null object design pattern, which makes me glad because I think it is horrid. But your Maybe class below is a watered down, weak version that (in my opinion) isn't worth bothering with. See below. class Maybe: def __getattr__(self, attr): return None def __getitem__(self, idx): return None def __call__(self, *args, **kw): return None def maybe(obj): return Maybe() if obj is None else obj And in action: py> maybe("spam").upper() # Works fine. 'SPAM' py> maybe(None).upper() Traceback (most recent call last): File "<stdin>", line 1, in <module> TypeError: 'NoneType' object is not callable It also fails for chained lookups: maybe(obj).spam['id'].ham will fail for the same reason. You could write this: maybe(maybe(obj).upper)() maybe(maybe(maybe(obj).spam)['id']).ham but that's simply awful. Avoiding that problem is why the Null object returns itself, but we've rightly ruled that out. This is why I think that if this is worth doing, it has to be some sort of short-circuiting operator or pseudo-operator: expression ? .spam.eggs.cheese can short-circuit the entire chain .spam.eggs.cheese, not just the first component. Otherwise, I don't think it's worth doing. -- Steve